You are given a permutation P_1 ... P_N of the set {1, 2, ..., N}.

You can apply the following operation to this permutation, any number of times (possibly zero):

* Choose two indices i,j (1 ≦ i < j ≦ N), such that j - i ≧ K and |P_i - P_j| = 1. Then, swap the values of P_i and P_j.



Among all permutations that can be obtained by applying this operation to the given permutation, find the lexicographically smallest one.

Constraints

* 2≦N≦500,000
* 1≦K≦N-1
* P is a permutation of the set {1, 2, ..., N}.

Input

The input is given from Standard Input in the following format:


N K
P_1 P_2 ... P_N


Output

Print the lexicographically smallest permutation that can be obtained.

Examples

Input

4 2
4 2 3 1


Output

2
1
4
3


Input

5 1
5 4 3 2 1


Output

1
2
3
4
5


Input

8 3
4 5 7 8 3 1 2 6


Output

1
2
6
7
5
3
4
8
#include <bits/stdc++.h>
using namespace std;
int getnum() {
  char ch = getchar();
  int x = 0, f = 1;
  while (ch < '0' || ch > '9') {
    if (ch == '-') f = -1;
    ch = getchar();
  }
  while (ch >= '0' && ch <= '9') {
    x = x * 10 + ch - '0';
    ch = getchar();
  }
  return x * f;
}
const int N = 500010, M = 500010, INF = 1000000010;
int n, k;
int cnt;
int head[N];
struct edge {
  int v, nxt;
} vec[M];
int ind[N];
int A[N];
int P[N];
int minn[N << 2];
priority_queue<int, vector<int>, greater<int> > Q;
int tot;
int ans[N];
void addedge(int u, int v) {
  vec[++cnt] = (edge){v, head[u]};
  head[u] = cnt;
  ++ind[v];
}
void get_read() {
  n = getnum();
  k = getnum();
  for (int i = 1; i <= n; ++i) A[P[i] = getnum()] = i;
}
void TOPSORT() {
  for (int i = 1; i <= n; ++i)
    if (!ind[i]) Q.push(i);
  while (!Q.empty()) {
    int u = Q.top();
    Q.pop();
    ans[u] = ++tot;
    for (int i = head[u]; i; i = vec[i].nxt) {
      int v = vec[i].v;
      --ind[v];
      if (!ind[v]) Q.push(v);
    }
  }
}
int query(int o, int l, int r, int L, int R) {
  if (L > R) return INF;
  if (L <= l && r <= R) return minn[o];
  int mid = (l + r) >> 1, ret = INF;
  if (L <= mid) ret = min(ret, query((o << 1), l, mid, L, R));
  if (R > mid) ret = min(ret, query((o << 1 | 1), mid + 1, r, L, R));
  return ret;
}
void modify(int o, int l, int r, int p, int w) {
  if (l == r) {
    minn[o] = w;
    return;
  }
  int mid = (l + r) >> 1;
  if (p <= mid)
    modify((o << 1), l, mid, p, w);
  else
    modify((o << 1 | 1), mid + 1, r, p, w);
  minn[o] = min(minn[(o << 1)], minn[(o << 1 | 1)]);
}
void get_work() {
  memset(minn, 63, sizeof(minn));
  for (int i = n; i >= 1; --i) {
    int t;
    t = query(1, 1, n, A[i] + 1, min(n, A[i] + k - 1));
    if (t < INF) addedge(A[i], A[t]);
    t = query(1, 1, n, max(1, A[i] - k + 1), A[i] - 1);
    if (t < INF) addedge(A[i], A[t]);
    modify(1, 1, n, A[i], i);
  }
  TOPSORT();
  for (int i = 1; i <= n; ++i) printf("%d\n", ans[i]);
}
int main() {
  get_read();
  get_work();
  return 0;
}
