Problem:
Score : 800 points

Problem Statement

Let N be a positive even number.

We have a permutation of (1, 2, ..., N), p = (p_1, p_2, ..., p_N).
Snuke is constructing another permutation of (1, 2, ..., N), q, following the procedure below.

First, let q be an empty sequence.
Then, perform the following operation until p becomes empty:

Select two adjacent elements in p, and call them x and y in order. Remove x and y from p (reducing the length of p by 2), and insert x and y, preserving the original order, at the beginning of q.

When p becomes empty, q will be a permutation of (1, 2, ..., N).

Find the lexicographically smallest permutation that can be obtained as q.

Constraints

N is an even number.

2 ≤ N ≤ 2 × 10^5

p is a permutation of (1, 2, ..., N).

Input

Input is given from Standard Input in the following format:

N
p_1 p_2 ... p_N

Output

Print the lexicographically smallest permutation, with spaces in between.

Sample Input 1

4
3 2 4 1

Sample Output 1

3 1 2 4

The solution above is obtained as follows:

p

q

(3, 2, 4, 1)

()

↓

↓

(3, 1)

(2, 4)

↓

↓

()

(3, 1, 2, 4)

Sample Input 2

2
1 2

Sample Output 2

1 2

Sample Input 3

8
4 6 3 2 8 5 7 1

Sample Output 3

3 1 2 7 4 6 8 5

The solution above is obtained as follows:

p

q

(4, 6, 3, 2, 8, 5, 7, 1)

()

↓

↓

(4, 6, 3, 2, 7, 1)

(8, 5)

↓

↓

(3, 2, 7, 1)

(4, 6, 8, 5)

↓

↓

(3, 1)

(2, 7, 4, 6, 8, 5)

↓

↓

()

(3, 1, 2, 7, 4, 6, 8, 5)

Solution in C++14 (GCC 5.4.1) (judge verdict: Wrong Answer)

#include <bits/stdc++.h>
using namespace std;
#define repl(i,a,b) for(int i=(int)(a);i<(int)(b);i++)
#define rep(i,n) repl(i,0,n)
#define mp(a,b) make_pair((a),(b))
#define pb(a) push_back((a))
#define all(x) (x).begin(),(x).end()
#define uniq(x) sort(all(x)),(x).erase(unique(all(x)),end(x))
#define fi first
#define se second
#define dbg(...) _dbg(#__VA_ARGS__, __VA_ARGS__)
void _dbg(string){cout<<endl;}
template<class H,class... T> void _dbg(string s,H h,T... t){int l=s.find(',');cout<<s.substr(0,l)<<" = "<<h<<", ";_dbg(s.substr(l+1),t...);}
template<class T,class U> ostream& operator<<(ostream& o, const pair<T,U> &p){o<<"("<<p.fi<<","<<p.se<<")";return o;}
template<class T> ostream& operator<<(ostream& o, const vector<T> &v){o<<"[";for(T t:v){o<<t<<",";}o<<"]";return o;}

#define INF 1120000000

template<typename T> // INFに注意
class SegTree {
private:
  int n;
  vector<T> data;
  T _query(int a, int b, int k, int l, int r){
    if(r<=a || b<=l) return INF;
    if(a<=l && r<=b) return data[k];
    T vl=_query(a,b,k*2+1,l,(l+r)/2);
    T vr=_query(a,b,k*2+2,(l+r)/2,r);
    return min(vl,vr);
  }
public:
  SegTree(int n_){
    n=1;
    while(n<n_) n*=2;
    data.resize(2*n-1);
    fill(all(data), INF);
  }
  void update(int k, T a){ // update data[k]=a, k(0-indexed)
    k+=n-1;
    data[k]=a;
    while(k>0){
      k = (k-1)/2;
      data[k] = min(data[k*2+1], data[k*2+2]);
    }
  }
  inline T query(int a, int b){ return _query(a,b,0,0,n);} //min value in [a,b)
  inline T operator[](int idx){ return data[idx+n-1]; }
}; // END class SegTree


int main(){
  int n;
  cin>>n;
  vector<int> vec(n);
  rep(i,n) cin>>vec[i], vec[i]--;
  vector<int> pos(n);
  rep(i,n) pos[vec[i]] = i;
// dbg(vec);
  SegTree<int> even(n+1), odd(n+1);
  rep(i,n){
    if(i%2) odd.update(i, vec[i]);
    else even.update(i, vec[i]);
  }

  vector<bool> used(n,false);
  vector<int> ans;
  set<int> wall;
  wall.insert(-1);
  wall.insert(n);

  rep(i,n) if(!used[i]){
    int p1 = pos[i];
    int p2;
    bool sw = false;
    auto itr = wall.upper_bound(p1);
    int r = *itr;
    itr--;
    int l = *itr;
    if(p1%2==0){
      if((p1-l)%2==1) p2 = odd.query(p1, r);
      else sw=true,p2 = odd.query(l+1, p1);
      assert(p2!=INF);
      p2 = pos[p2];
      odd.update(p2, INF);
      even.update(p1, INF);
    }
    else {
      if((p1-l)%2==1) p2 = even.query(p1, r);
      else sw=true, p2 = even.query(l+1, p1);
      assert(p2!=INF);
      p2 = pos[p2];
      even.update(p2, INF);
      odd.update(p1, INF);
    }
    if(sw) swap(p1,p2);
    ans.pb(vec[p1]);ans.pb(vec[p2]);
    used[vec[p1]] = used[vec[p2]] = true;
    wall.insert(p1);
    wall.insert(p2);
  }

  rep(i,n) cout << ans[i]+1 << " \n"[i==n-1];

  return 0;
}