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 PyPy3 (2.4.0) (judge verdict: Time Limit Exceeded)

class SegmentTree:#抽象セグ木
    def __init__(self, N, id, fun):#id:単位元
        self.N0 = 2**(N-1).bit_length()
        self.id = id
        self.data = [self.id]*(2*self.N0)
        self.fun = fun
    def update(self, k, x, update_fun):
        k+=self.N0-1
        self.data[k] = update_fun(self.data[k], x)
        while k>=0:
            k = (k-1)//2
            self.data[k] = self.fun(self.data[2*k+1], self.data[2*k+2])
    def query(self, l, r):#[l, r)
        L = l+self.N0; R = r+self.N0
        s = self.id
        while L<R:
            if R&1:
                R-=1
                s = self.fun(s, self.data[R-1])
            if L&1:
                s = self.fun(s, self.data[L-1])
                L+=1
            L >>= 1; R>>=1
        return s
def main():
    import sys
    input = sys.stdin.readline
    inf = 10**18
    N = int(input())
    p = list(map(int, input().split()))
    d = [0]*(N+1)
    for i in range(N):
        d[p[i]] = i
    S1 = SegmentTree(N//2, inf, min)
    S2 = SegmentTree(N//2, inf, min)
    res = []
    def add(l, r):
        if r-l<2:
            return
        if l%2 == 0:
            x = S1.query(l//2, r//2)
            i = d[x]
        else:
            x = S2.query(l//2, r//2)
            i = d[x]
        heappush(que, (x, i, l, r))

    from heapq import heappop, heappush
    f = lambda x, y:y
    for i, x in enumerate(p[::2]):
        S1.update(i, x, f)
    for i, x in enumerate(p[1::2]):
        S2.update(i, x, f)
    x = S1.query(0, N//2)
    i = d[x]
    que = [(x, i, 0, N)]
    while que:
        x, i, l, r = heappop(que)
        if r-l==2:
            res.append(p[l])
            res.append(p[l+1])
            continue
        if r-l<2:
            continue
        if l%2 == 0:
            y = S2.query(i//2, r//2)
            j = d[y]
        else:
            y = S1.query(i//2+1, r//2+1)
            j = d[y]
        res.append(x)
        res.append(y)
        add(l, i)
        add(i+1, j)
        add(j+1, r)
    print(*res)
main()