This is an interactive task.

Dasha and NN like playing chess. While playing a match they decided that normal chess isn't interesting enough for them, so they invented a game described below.

There are $666$ black rooks and $1$ white king on the chess board of size $999 \times 999$. The white king wins if he gets checked by rook, or, in other words, if he moves onto the square which shares either a row or column with a black rook.

The sides take turns, starting with white. NN plays as a white king and on each of his turns he moves a king to one of the squares that are adjacent to his current position either by side or diagonally, or, formally, if the king was on the square $(x, y)$, it can move to the square $(nx, ny)$ if and only $\max (|nx - x|, |ny - y|) = 1$, $1 \leq nx, ny \leq 999$. NN is also forbidden from moving onto the squares occupied with black rooks, however, he can move onto the same row or column as a black rook.

Dasha, however, neglects playing by the chess rules, and instead of moving rooks normally she moves one of her rooks on any space devoid of other chess pieces. It is also possible that the rook would move onto the same square it was before and the position wouldn't change. However, she can't move the rook on the same row or column with the king.

Each player makes $2000$ turns, if the white king wasn't checked by a black rook during those turns, black wins.

NN doesn't like losing, but thinks the task is too difficult for him, so he asks you to write a program that will always win playing for the white king. Note that Dasha can see your king and play depending on its position.

Input

In the beginning your program will receive $667$ lines from input. Each line contains two integers $x$ and $y$ ($1 \leq x, y \leq 999$) — the piece's coordinates. The first line contains the coordinates of the king and the next $666$ contain the coordinates of the rooks. The first coordinate denotes the number of the row where the piece is located, the second denotes the column. It is guaranteed that initially the king isn't in check and that all pieces occupy different squares.

Output

After getting king checked, you program should terminate immediately without printing anything extra.

Interaction

To make a move with the king, output two integers $x$ and $y$ ($1 \leq x, y \leq 999$) — the square to which the king would be moved. The king cannot move onto the square already occupied by a rook. It is guaranteed that the king would always have a valid move.

After each of your turns read the rook's turn in the following format: a single line containing three integers $k$, $x$ and $y$ ($1 \leq k \leq 666$, $1 \leq x_i, y_i \leq 999$) — the number of the rook that would move and the square it would move to. It is guaranteed that the rook wouldn't move to a square already occupied by another chess piece, but it can move onto the square where it was before the turn so that its position wouldn't change. It is guaranteed that the move does not put your king into a check. If your king got in check, all three integers would be equal to $-1$ and in that case your program should terminate immediately.

After printing your turn do not forget to output end of line and flush the output. Otherwise you will get Idleness limit exceeded. To do this, use:

* fflush(stdout) or cout.flush() in C++;
* System.out.flush() in Java;
* flush(output) in Pascal;
* stdout.flush() in Python;
* see documentation for other languages.

Answer "0 0 0" instead of a correct answer means that you made an invalid query. Exit immediately after receiving "0 0 0" and you will see Wrong answer verdict. Otherwise you can get an arbitrary verdict because your solution will continue to read from a closed stream.

Example

Input

```
999 999
1 1
1 2
2 1
2 2
1 3
2 3
<...>
26 13
26 14
26 15
26 16

1 700 800

2 1 2

<...>

-1 -1 -1
```

Output

```
999 998

999 997

<...>

999 26
```

Note

The example is trimmed. The full initial positions of the rooks in the first test are available at [link omitted]. It is not guaranteed that they will behave as in the example.

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

static long long queries = 0;
static long long query_limit = 0;

static void log_metrics() {
    try {
        tout << "queries=" << queries << "\n";
        tout << "query_limit=" << query_limit << "\n";
        tout.flush();
    } catch (...) {

    }
}

static void finish(TResult verdict, const string& msg) {
    log_metrics();
    quitf(verdict, "%s", msg.c_str());
}

static bool readToken(string& s) {
    s.clear();
    if (!(cin >> s)) return false;
    return true;
}

static bool parseLL(const string& s, long long& v) {
    if (s.empty()) return false;
    int i = 0;
    if (s[0] == '-') i = 1;
    if (i == (int)s.size()) return false;
    for (; i < (int)s.size(); i++) {
        if (s[i] < '0' || s[i] > '9') return false;
    }
    try {
        size_t pos = 0;
        long long x = stoll(s, &pos, 10);
        if (pos != s.size()) return false;
        v = x;
        return true;
    } catch (...) {
        return false;
    }
}

static bool readLL(long long& v) {
    string s;
    if (!readToken(s)) return false;
    return parseLL(s, v);
}

int main(int argc, char** argv) {
    registerInteraction(argc, argv);
    atexit(log_metrics);

    const int B = 999;
    const int R = 666;

    int kx = inf.readInt(1, B, "king_x");
    int ky = inf.readInt(1, B, "king_y");
    vector<pair<int,int>> rooks;
    rooks.reserve(R);
    for (int i = 0; i < R; i++) {
        int x = inf.readInt(1, B, "rook_x");
        int y = inf.readInt(1, B, "rook_y");
        rooks.push_back({x, y});
    }

    query_limit = 2000;
    log_metrics();

    cout << kx << " " << ky << "\n";
    for (auto [x, y] : rooks) cout << x << " " << y << "\n";
    cout.flush();

    vector<vector<char>> occ(B + 1, vector<char>(B + 1, 0));
    occ[kx][ky] = 1;
    for (auto [x, y] : rooks) occ[x][y] = 1;

    auto inBounds = [&](int x, int y) -> bool { return 1 <= x && x <= B && 1 <= y && y <= B; };

    auto inCheck = [&]() -> bool {
        for (auto [x, y] : rooks) {
            if (x == kx || y == ky) return true;
        }
        return false;
    };

    auto sendInvalid = [&]() {
        cout << "0 0 0\n";
        cout.flush();
    };

    const long long hard_cap = max(200000LL, 10LL * query_limit);

    for (int turn = 1; turn <= (int)query_limit; turn++) {
        long long nxLL, nyLL;
        if (!readLL(nxLL) || !readLL(nyLL)) {
            finish(_pe, "unexpected EOF / malformed king move");
        }
        queries++;
        if (queries > hard_cap) {
            finish(_pe, "hard cap exceeded");
        }

        if (!inBounds((int)nxLL, (int)nyLL)) {
            sendInvalid();
            finish(_wa, "king move out of bounds");
        }

        int nx = (int)nxLL, ny = (int)nyLL;
        int dx = abs(nx - kx), dy = abs(ny - ky);
        if (max(dx, dy) != 1) {
            sendInvalid();
            finish(_wa, "king move not adjacent");
        }
        if (occ[nx][ny]) {
            sendInvalid();
            finish(_wa, "king moved onto occupied square");
        }

        occ[kx][ky] = 0;
        kx = nx; ky = ny;
        occ[kx][ky] = 1;

        if (inCheck()) {
            cout << "-1 -1 -1\n";
            cout.flush();
            finish(_ok, "king is checked");
        }

        int rk = 1;
        int rx = rooks[0].first;
        int ry = rooks[0].second;

        if (rx == kx || ry == ky) {

            finish(_fail, "internal error: rook shares row/col with king while not in check");
        }

        cout << rk << " " << rx << " " << ry << "\n";
        cout.flush();
    }

    finish(_wa, "king not checked within 2000 turns");
}

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

static long long queries = 0;
static long long query_limit = 0;

static void log_metrics() {
    try {
        tout << "queries=" << queries << "\n";
        tout << "query_limit=" << query_limit << "\n";
        tout.flush();
    } catch (...) {

    }
}

static void finish(TResult verdict, const string& msg) {
    log_metrics();
    quitf(verdict, "%s", msg.c_str());
}

static inline int idx(int x, int y) { return x * 1000 + y; }

static bool inb(int v, int B) { return 1 <= v && v <= B; }

static bool is_int_token(const string& s) {
    if (s.empty()) return false;
    int i = 0;
    if (s[0] == '-') {
        if (s.size() == 1) return false;
        i = 1;
    }
    for (; i < (int)s.size(); i++) if (s[i] < '0' || s[i] > '9') return false;
    return true;
}

static bool read_ll(long long& out) {
    string tok;
    if (!(cin >> tok)) return false;
    if (!is_int_token(tok)) return false;
    try {
        size_t p = 0;
        long long v = stoll(tok, &p);
        if (p != tok.size()) return false;
        out = v;
        return true;
    } catch (...) {
        return false;
    }
}

struct MoveChoice {
    int k = 1;
    int x = 1;
    int y = 1;
    bool moved = false;
};

static pair<int,int> pick_square_far(int B, int kx, int ky, const vector<int>& board) {
    auto ok_strict = [&](int x, int y) -> bool {
        if (!inb(x, B) || !inb(y, B)) return false;
        if (x == kx || y == ky) return false;
        if (abs(x - kx) < 2) return false;
        if (abs(y - ky) < 2) return false;
        if (board[idx(x, y)] != -1) return false;
        return true;
    };
    auto ok_relaxed = [&](int x, int y) -> bool {
        if (!inb(x, B) || !inb(y, B)) return false;
        if (x == kx || y == ky) return false;
        if (board[idx(x, y)] != -1) return false;
        return true;
    };

    auto farX = [&](int d, bool primary) -> int {
        bool kingLow = (kx <= B / 2);
        if (!primary) kingLow = !kingLow;
        return kingLow ? (B - d) : (1 + d);
    };
    auto farY = [&](int d, bool primary) -> int {
        bool kingLow = (ky <= B / 2);
        if (!primary) kingLow = !kingLow;
        return kingLow ? (B - d) : (1 + d);
    };

    for (int pass = 0; pass < 2; pass++) {
        for (int d = 0; d <= B - 1; d++) {
            int x1 = farX(d, true), x2 = farX(d, false);
            int y1 = farY(d, true), y2 = farY(d, false);
            pair<int,int> cand[4] = {{x1,y1},{x1,y2},{x2,y1},{x2,y2}};
            for (auto [x, y] : cand) {
                if (pass == 0 ? ok_strict(x, y) : ok_relaxed(x, y)) return {x, y};
            }
        }
    }

    return { (kx == 1 ? 2 : 1), (ky == 1 ? 2 : 1) };
}

static MoveChoice choose_dasha_move(
    int B,
    int kx, int ky,
    vector<pair<int,int>>& rooks,
    vector<int>& board,
    vector<int>& rowCount,
    vector<int>& colCount
) {
    vector<int> badRows, badCols;
    if (kx - 1 >= 1) badRows.push_back(kx - 1);
    if (kx + 1 <= B) badRows.push_back(kx + 1);
    if (ky - 1 >= 1) badCols.push_back(ky - 1);
    if (ky + 1 <= B) badCols.push_back(ky + 1);

    auto in_list = [&](int v, const vector<int>& lst) -> bool {
        for (int x : lst) if (x == v) return true;
        return false;
    };

    int bestIdx = 0;
    long long bestScore = LLONG_MIN;

    for (int i = 0; i < (int)rooks.size(); i++) {
        int rx = rooks[i].first, ry = rooks[i].second;
        int rd = abs(rx - kx);
        int cd = abs(ry - ky);

        long long score = 0;
        bool immediate = in_list(rx, badRows) || in_list(ry, badCols);
        bool near2 = (abs(rx - kx) == 2) || (abs(ry - ky) == 2);

        if (immediate) score += 1000000000LL;
        if (near2) score += 10000000LL;

        if (rd == 1) score += 1000000;
        if (cd == 1) score += 1000000;
        if (rd == 2) score += 10000;
        if (cd == 2) score += 10000;
        if (rd == 3) score += 100;
        if (cd == 3) score += 100;

        score = score * 1000 - i;

        if (score > bestScore) {
            bestScore = score;
            bestIdx = i;
        }
    }

    MoveChoice res;
    res.k = bestIdx + 1;

    int rx = rooks[bestIdx].first, ry = rooks[bestIdx].second;
    bool shouldMove = (abs(rx - kx) <= 2) || (abs(ry - ky) <= 2);

    if (!shouldMove) {
        res.x = rx;
        res.y = ry;
        res.moved = false;
        return res;
    }

    board[idx(rx, ry)] = -1;
    rowCount[rx]--;
    colCount[ry]--;

    auto [nx, ny] = pick_square_far(B, kx, ky, board);

    rooks[bestIdx] = {nx, ny};
    board[idx(nx, ny)] = res.k;
    rowCount[nx]++;
    colCount[ny]++;

    res.x = nx;
    res.y = ny;
    res.moved = true;
    return res;
}

int main(int argc, char** argv) {
    registerInteraction(argc, argv);
    atexit(log_metrics);

    const int B = 999;
    const int R = 666;
    query_limit = 2000;
    const long long hard_cap = max(200000LL, 10LL * query_limit);

    log_metrics();

    int kx = inf.readInt(1, B, "king_x");
    int ky = inf.readInt(1, B, "king_y");

    vector<pair<int,int>> rooks;
    rooks.reserve(R);

    vector<int> board(1000 * 1000, -1);
    vector<int> rowCount(B + 1, 0), colCount(B + 1, 0);

    board[idx(kx, ky)] = -2;

    for (int i = 1; i <= R; i++) {
        int x = inf.readInt(1, B, ("rook_x_" + to_string(i)).c_str());
        int y = inf.readInt(1, B, ("rook_y_" + to_string(i)).c_str());
        if (board[idx(x, y)] != -1) finish(_pe, "invalid hidden input: duplicate piece square");
        if (x == kx || y == ky) finish(_pe, "invalid hidden input: king initially in check");
        rooks.push_back({x, y});
        board[idx(x, y)] = i;
        rowCount[x]++;
        colCount[y]++;
    }

    cout << kx << " " << ky << "\n";
    for (int i = 0; i < R; i++) {
        cout << rooks[i].first << " " << rooks[i].second << "\n";
    }
    cout.flush();

    for (int turn = 1; turn <= (int)query_limit; turn++) {
        long long nx_ll, ny_ll;
        if (!read_ll(nx_ll) || !read_ll(ny_ll)) {
            finish(_wa, "unexpected EOF or malformed king move");
        }
        queries++;
        if (queries > hard_cap) finish(_pe, "too many queries");

        if (nx_ll < 1 || nx_ll > B || ny_ll < 1 || ny_ll > B) {
            cout << "0 0 0" << endl;
            finish(_wa, "king move out of bounds");
        }

        int nx = (int)nx_ll, ny = (int)ny_ll;
        int dx = abs(nx - kx), dy = abs(ny - ky);
        if (max(dx, dy) != 1) {
            cout << "0 0 0" << endl;
            finish(_wa, "king move not adjacent");
        }
        if (board[idx(nx, ny)] >= 1) {
            cout << "0 0 0" << endl;
            finish(_wa, "king moved onto a rook square");
        }

        board[idx(kx, ky)] = -1;
        kx = nx; ky = ny;
        board[idx(kx, ky)] = -2;

        if (rowCount[kx] > 0 || colCount[ky] > 0) {
            cout << "-1 -1 -1" << endl;
            finish(_ok, "king is checked (wins)");
        }

        MoveChoice mv = choose_dasha_move(B, kx, ky, rooks, board, rowCount, colCount);

        if (!inb(mv.k, R) || !inb(mv.x, B) || !inb(mv.y, B)) finish(_pe, "internal: illegal rook move generated");
        if (mv.x == kx || mv.y == ky) finish(_pe, "internal: rook moved onto king row/col");
        if (board[idx(mv.x, mv.y)] != mv.k) finish(_pe, "internal: rook placement mismatch");
        if (rowCount[kx] != 0 || colCount[ky] != 0) finish(_pe, "internal: king in check after rook move");

        cout << mv.k << " " << mv.x << " " << mv.y << endl;
    }

    finish(_wa, "king was not checked within 2000 turns");
}

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

static int distToSegment(int v, int l, int r) {
    if (v < l) return l - v;
    if (v > r) return v - r;
    return 0;
}

static int pickSegmentStartAvoid(int B, int len, int forbidden, int ref, int extraTries) {
    int maxStart = B - len + 1;
    ensure(maxStart >= 1);

    auto valid = [&](int s) -> bool {
        if (s < 1 || s > maxStart) return false;
        int l = s, r = s + len - 1;
        return !(l <= forbidden && forbidden <= r);
    };

    auto score = [&](int s) -> int {
        int l = s, r = s + len - 1;
        return distToSegment(ref, l, r);
    };

    vector<int> cand;
    cand.push_back(1);
    cand.push_back(maxStart);
    cand.push_back(max(1, min(maxStart, ref - len / 2)));
    cand.push_back(max(1, min(maxStart, forbidden - len)));
    cand.push_back(max(1, min(maxStart, forbidden + 1)));
    cand.push_back(max(1, min(maxStart, forbidden - len / 2)));

    int bestS = -1, bestScore = -1;
    for (int s : cand) {
        if (!valid(s)) continue;
        int sc = score(s);
        if (sc > bestScore) {
            bestScore = sc;
            bestS = s;
        }
    }

    for (int i = 0; i < extraTries; i++) {
        int s = rnd.next(1, maxStart);
        if (!valid(s)) continue;
        int sc = score(s);
        if (sc > bestScore) {
            bestScore = sc;
            bestS = s;
        }
    }

    if (bestS != -1) return bestS;

    for (int s = 1; s <= maxStart; s++) {
        if (valid(s)) return s;
    }
    ensure(false);
    return 1;
}

static vector<pair<int,int>> genBlock(int B, int R, int kx, int ky, int a, int b) {
    ensure(1 <= a && a <= B);
    ensure(1 <= b && b <= B);
    ensure(1 <= kx && kx <= B);
    ensure(1 <= ky && ky <= B);
    ensure(a < B && b < B);

    int rowStart = pickSegmentStartAvoid(B, a, kx, kx, 40);
    int colStart = pickSegmentStartAvoid(B, b, ky, ky, 40);

    vector<pair<int,int>> rooks;
    rooks.reserve(R);
    for (int i = 0; i < a && (int)rooks.size() < R; i++) {
        int x = rowStart + i;
        ensure(x != kx);
        for (int j = 0; j < b && (int)rooks.size() < R; j++) {
            int y = colStart + j;
            ensure(y != ky);
            rooks.push_back({x, y});
        }
    }
    ensure((int)rooks.size() == R);
    return rooks;
}

static vector<pair<int,int>> genCross(int B, int R, int kx, int ky, int r, int c) {
    ensure(1 <= r && r <= B);
    ensure(1 <= c && c <= B);
    ensure(r != kx);
    ensure(c != ky);

    vector<pair<int,int>> rooks;
    rooks.reserve(R);

    int first = R / 2;
    for (int y = 1; y <= B && (int)rooks.size() < first; y++) {
        if (y == ky) continue;
        rooks.push_back({r, y});
    }
    ensure((int)rooks.size() == first);

    for (int x = 1; x <= B && (int)rooks.size() < R; x++) {
        if (x == kx) continue;
        if (x == r) continue;
        rooks.push_back({x, c});
    }
    ensure((int)rooks.size() == R);
    return rooks;
}

int main(int argc, char* argv[]) {
    registerGen(argc, argv, 1);

    string mode = opt<string>("mode", "non");
    int B = opt<int>("board", 999);
    int R = opt<int>("rooks", 666);

    ensure(B == 999);
    ensure(R == 666);

    long long seed = 0;
    if (argc >= 2) seed = atoll(argv[1]);

    int kx = 500, ky = 500;
    vector<pair<int,int>> rooks;

    if (seed == 1) {
        kx = 1; ky = 1;

        int a = 27, b = 27;
        int rowStart = B - a + 1;
        int colStart = B - b + 1;
        rooks.reserve(R);
        for (int i = 0; i < a && (int)rooks.size() < R; i++) {
            for (int j = 0; j < b && (int)rooks.size() < R; j++) {
                rooks.push_back({rowStart + i, colStart + j});
            }
        }
    } else if (seed == 2) {
        kx = 500; ky = 500;

        int r = 1;
        int c = 1;
        if (r == kx) r = B;
        if (c == ky) c = B;
        rooks = genCross(B, R, kx, ky, r, c);
    } else if (seed == 3) {
        kx = B; ky = B;

        int a = 27, b = 27;
        int rowStart = 1;
        int colStart = 1;
        rooks.reserve(R);
        for (int i = 0; i < a && (int)rooks.size() < R; i++) {
            for (int j = 0; j < b && (int)rooks.size() < R; j++) {
                rooks.push_back({rowStart + i, colStart + j});
            }
        }
    } else {
        if (mode != "non" && mode != "adp") mode = "non";

        int lo = B / 3, hi = 2 * B / 3;
        kx = rnd.next(lo, hi);
        ky = rnd.next(lo, hi);

        if (mode == "non") {

            int a = rnd.next(18, 38);
            int b = (R + a - 1) / a;
            if (b < 18) b = 18;
            if (a * b < R) b++;
            if (a >= B) a = B - 1;
            if (b >= B) b = B - 1;
            while (a * b < R) {
                if (b + 1 < B) b++;
                else if (a + 1 < B) a++;
                else break;
            }
            ensure(a * b >= R);
            rooks = genBlock(B, R, kx, ky, a, b);
        } else {

            int r = (kx <= B / 2 ? B : 1);
            int c = (ky <= B / 2 ? B : 1);
            if (r == kx) r = (r == 1 ? B : 1);
            if (c == ky) c = (c == 1 ? B : 1);
            rooks = genCross(B, R, kx, ky, r, c);
        }
    }

    ensure((int)rooks.size() == R);

    set<pair<int,int>> used;
    used.insert({kx, ky});
    for (auto [x, y] : rooks) {
        ensure(1 <= x && x <= B);
        ensure(1 <= y && y <= B);
        ensure(x != kx && y != ky);
        ensure(!used.count({x, y}));
        used.insert({x, y});
    }

    cout << kx << " " << ky << "\n";
    for (auto [x, y] : rooks) {
        cout << x << " " << y << "\n";
    }
    return 0;
}


This is an interactive problem.

You are given a tree consisting of $n$ nodes numbered with integers from $1$ to $n$. Ayush and Ashish chose two secret distinct nodes in the tree. You need to find out both the nodes. You can make the following query:

* Provide a list of nodes and you will receive a node from that list whose sum of distances to both the hidden nodes is minimal (if there are multiple such nodes in the list, you will receive any one of them). You will also get the sum of distances of that node to the hidden nodes.

Recall that a tree is a connected graph without cycles. The distance between two nodes is defined as the number of edges in the simple path between them.

More formally, let's define two hidden nodes as $s$ and $f$. In one query you can provide the set of nodes $\{a_1, a_2, \ldots, a_c\}$ of the tree. As a result, you will get two numbers $a_i$ and $dist(a_i, s) + dist(a_i, f)$. The node $a_i$ is any node from the provided set, for which the number $dist(a_i, s) + dist(a_i, f)$ is minimal.

You can ask no more than $14$ queries.

Input

The first line contains a single integer $t$ $(1 \leq t \leq 10)$ — the number of test cases. Please note, how the interaction process is organized.

The first line of each test case consists of a single integer $n$ $(2 \le n \le 1000)$ — the number of nodes in the tree.

The next $n - 1$ lines consist of two integers $u$, $v$ $(1 \le u, v \le n, u \ne v)$ — the edges of the tree.

Interaction

To ask a query print a single line:

* In the beginning print "? c " (without quotes) where $c$ $(1 \leq c \leq n)$ denotes the number of nodes being queried, followed by $c$ distinct integers in the range $[1, n]$  — the indices of nodes from the list.

For each query, you will receive two integers $x$, $d$ — the node (among the queried nodes) with the minimum sum of distances to the hidden nodes and the sum of distances from that node to the hidden nodes. If the subset of nodes queried is invalid or you exceeded the number of queries then you will get $x = d = -1$. In this case, you should terminate the program immediately.

When you have guessed the hidden nodes, print a single line "! " (without quotes), followed by two integers in the range $[1, n]$  — the hidden nodes. You can output the hidden nodes in any order.

After this, you should read a string. If you guess the nodes correctly, you will receive the string "Correct". In this case, you should continue solving the remaining test cases or terminate the program, if all test cases were solved. Otherwise, you will receive the string "Incorrect". In this case, you should terminate the program immediately.

Guessing the hidden nodes does not count towards the number of queries asked.

The interactor is not adaptive. The hidden nodes do not change with queries.

Do not forget to read the string "Correct" / "Incorrect" after guessing the hidden nodes.

You need to solve each test case before receiving the input for the next test case.

The limit of $14$ queries applies to each test case and not to the entire input.

After printing a query do not forget to output the end of the line and flush the output. Otherwise, you will get Idleness limit exceeded. To do this, use:

* fflush(stdout) or cout.flush() in C++;
* System.out.flush() in Java;
* flush(output) in Pascal;
* stdout.flush() in Python;
* see the documentation for other languages.

Example

Input

```
1
3
1 2
1 3

1 1

2 3

3 1

3 1

Correct
```

Output

```
? 1 1

? 1 2

? 1 3

? 2 2 3

! 1 3
```

Note

The tree from the first test is shown below, and the hidden nodes are $1$ and $3$.

![](https://espresso.codeforces.com/bcbd6776c018650322ba173e0c6ba8ca885688ab.png)

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

static long long queries = 0;
static long long query_limit = 0;

static void log_metrics() {
    try {
        tout << "queries=" << queries << "\n";
        tout << "query_limit=" << query_limit << "\n";
        tout.flush();
    } catch (...) {

    }
}

static void finish(TResult verdict, const string& msg) {
    log_metrics();
    quitf(verdict, "%s", msg.c_str());
}

static vector<int> bfs_dist(int n, const vector<vector<int>>& g, int src) {
    vector<int> dist(n + 1, -1);
    queue<int> q;
    dist[src] = 0;
    q.push(src);
    while (!q.empty()) {
        int v = q.front();
        q.pop();
        for (int to : g[v]) {
            if (dist[to] != -1) continue;
            dist[to] = dist[v] + 1;
            q.push(to);
        }
    }
    return dist;
}

int main(int argc, char** argv) {
    registerInteraction(argc, argv);
    atexit(log_metrics);

    try {
        int t = inf.readInt(1, 10, "t");
        query_limit = 14;
        const long long hard_cap = max(200000LL, 10LL * query_limit);

        log_metrics();

        cout << t << "\n";
        cout.flush();

        for (int tc = 1; tc <= t; tc++) {
            int n = inf.readInt(2, 1000, "n");

            vector<pair<int, int>> edges;
            edges.reserve(max(0, n - 1));

            vector<vector<int>> g(n + 1);
            for (int i = 0; i < n - 1; i++) {
                int u = inf.readInt(1, n, "u");
                int v = inf.readInt(1, n, "v");
                if (u == v) finish(_pe, "Hidden input invalid: self-loop");
                edges.push_back({u, v});
                g[u].push_back(v);
                g[v].push_back(u);
            }

            int s = inf.readInt(1, n, "s");
            int f = inf.readInt(1, n, "f");
            if (s == f) finish(_pe, "Hidden input invalid: s==f");

            vector<int> distS = bfs_dist(n, g, s);
            vector<int> distF = bfs_dist(n, g, f);
            for (int i = 1; i <= n; i++) {
                if (distS[i] < 0 || distF[i] < 0) finish(_pe, "Hidden input invalid: graph not connected");
            }

            cout << n << "\n";
            for (auto [u, v] : edges) cout << u << " " << v << "\n";
            cout.flush();

            while (true) {
                string cmd;
                if (!(cin >> cmd)) finish(_pe, "Unexpected EOF from contestant");

                if (cmd == "?") {
                    long long c_ll;
                    if (!(cin >> c_ll)) finish(_pe, "Malformed query: missing c");
                    if (c_ll < 1 || c_ll > n) {
                        cout << "-1 -1\n";
                        cout.flush();
                        finish(_pe, "Invalid query: c out of range");
                    }
                    int c = (int)c_ll;

                    vector<int> seen(n + 1, 0);
                    vector<int> nodes;
                    nodes.reserve(c);
                    for (int i = 0; i < c; i++) {
                        long long x_ll;
                        if (!(cin >> x_ll)) finish(_pe, "Malformed query: missing node");
                        if (x_ll < 1 || x_ll > n) {
                            cout << "-1 -1\n";
                            cout.flush();
                            finish(_pe, "Invalid query: node out of range");
                        }
                        int x = (int)x_ll;
                        if (seen[x]) {
                            cout << "-1 -1\n";
                            cout.flush();
                            finish(_pe, "Invalid query: duplicate node");
                        }
                        seen[x] = 1;
                        nodes.push_back(x);
                    }

                    queries++;
                    if (queries > hard_cap) finish(_pe, "Hard cap exceeded (too many queries)");
                    log_metrics();

                    int best = nodes[0];
                    int bestVal = distS[best] + distF[best];
                    for (int v : nodes) {
                        int val = distS[v] + distF[v];
                        if (val < bestVal || (val == bestVal && v < best)) {
                            bestVal = val;
                            best = v;
                        }
                    }

                    cout << best << " " << bestVal << "\n";
                    cout.flush();
                } else if (cmd == "!") {
                    long long a_ll, b_ll;
                    if (!(cin >> a_ll >> b_ll)) finish(_pe, "Malformed answer: expected two integers");
                    if (a_ll < 1 || a_ll > n || b_ll < 1 || b_ll > n || a_ll == b_ll) {
                        cout << "Incorrect\n";
                        cout.flush();
                        finish(_wa, "Invalid final answer format/range");
                    }
                    int a = (int)a_ll, b = (int)b_ll;

                    bool ok = (a == s && b == f) || (a == f && b == s);
                    if (!ok) {
                        cout << "Incorrect\n";
                        cout.flush();
                        finish(_wa, "Wrong hidden nodes guessed");
                    }

                    cout << "Correct\n";
                    cout.flush();
                    break;
                } else {
                    cout << "-1 -1\n";
                    cout.flush();
                    finish(_pe, "Unknown command token");
                }
            }
        }

        finish(_ok, "All test cases solved");
    } catch (const std::exception& e) {
        finish(_pe, string("Exception: ") + e.what());
    } catch (...) {
        finish(_pe, "Unknown exception");
    }
}

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

static pair<int, vector<int>> bfs_farthest(int n, const vector<vector<int>>& g, int src) {
    vector<int> dist(n + 1, -1);
    queue<int> q;
    dist[src] = 0;
    q.push(src);
    int far = src;
    while (!q.empty()) {
        int v = q.front();
        q.pop();
        if (dist[v] > dist[far]) far = v;
        for (int to : g[v]) {
            if (dist[to] != -1) continue;
            dist[to] = dist[v] + 1;
            q.push(to);
        }
    }
    return {far, dist};
}

static pair<int, int> diameter_endpoints(int n, const vector<pair<int, int>>& edges) {
    vector<vector<int>> g(n + 1);
    g.reserve(n + 1);
    for (auto [u, v] : edges) {
        g[u].push_back(v);
        g[v].push_back(u);
    }
    int a = bfs_farthest(n, g, 1).first;
    int b = bfs_farthest(n, g, a).first;
    return {a, b};
}

static vector<pair<int, int>> build_path(int n) {
    vector<pair<int, int>> edges;
    edges.reserve(n - 1);
    for (int i = 1; i < n; i++) edges.push_back({i, i + 1});
    return edges;
}

static vector<pair<int, int>> build_star(int n, int center = 1) {
    vector<pair<int, int>> edges;
    edges.reserve(n - 1);
    for (int i = 1; i <= n; i++) {
        if (i == center) continue;
        edges.push_back({center, i});
    }
    return edges;
}

static vector<pair<int, int>> build_binary_heap(int n) {
    vector<pair<int, int>> edges;
    edges.reserve(n - 1);
    for (int i = 1; i <= n; i++) {
        int l = 2 * i;
        int r = 2 * i + 1;
        if (l <= n) edges.push_back({i, l});
        if (r <= n) edges.push_back({i, r});
    }
    return edges;
}

static vector<pair<int, int>> build_broom(int n, int handle_len) {
    handle_len = max(2, min(handle_len, n));
    vector<pair<int, int>> edges;
    edges.reserve(n - 1);
    for (int i = 1; i < handle_len; i++) edges.push_back({i, i + 1});
    int hub = handle_len;
    for (int v = handle_len + 1; v <= n; v++) edges.push_back({hub, v});
    return edges;
}

static vector<pair<int, int>> build_caterpillar(int n, int spine_len) {
    spine_len = max(2, min(spine_len, n));
    vector<pair<int, int>> edges;
    edges.reserve(n - 1);

    for (int i = 1; i < spine_len; i++) edges.push_back({i, i + 1});

    int next_node = spine_len + 1;
    while (next_node <= n) {
        int attach = rnd.next(1, spine_len);
        edges.push_back({attach, next_node});
        next_node++;
    }
    return edges;
}

static vector<pair<int, int>> build_double_broom(int n, int path_len, int left_leaves, int right_leaves) {
    path_len = max(2, min(path_len, n));
    int used = path_len + left_leaves + right_leaves;
    if (used > n) {
        int overflow = used - n;
        int take_from_right = min(overflow, right_leaves);
        right_leaves -= take_from_right;
        overflow -= take_from_right;
        left_leaves = max(0, left_leaves - overflow);
    }

    vector<pair<int, int>> edges;
    edges.reserve(n - 1);

    for (int i = 1; i < path_len; i++) edges.push_back({i, i + 1});
    int left_hub = 1;
    int right_hub = path_len;

    int cur = path_len + 1;
    for (int i = 0; i < left_leaves && cur <= n; i++, cur++) edges.push_back({left_hub, cur});
    for (int i = 0; i < right_leaves && cur <= n; i++, cur++) edges.push_back({right_hub, cur});

    while (cur <= n) {
        int attach = rnd.next(1, path_len);
        edges.push_back({attach, cur});
        cur++;
    }
    return edges;
}

static vector<pair<int, int>> build_prufer_tree(int n) {
    vector<int> prufer(max(0, n - 2));
    for (int i = 0; i < (int)prufer.size(); i++) prufer[i] = rnd.next(1, n);

    vector<int> degree(n + 1, 1);
    for (int x : prufer) degree[x]++;

    priority_queue<int, vector<int>, greater<int>> pq;
    for (int i = 1; i <= n; i++) if (degree[i] == 1) pq.push(i);

    vector<pair<int, int>> edges;
    edges.reserve(n - 1);

    for (int x : prufer) {
        int leaf = pq.top();
        pq.pop();
        edges.push_back({leaf, x});
        degree[leaf]--;
        degree[x]--;
        if (degree[x] == 1) pq.push(x);
    }
    int u = pq.top(); pq.pop();
    int v = pq.top(); pq.pop();
    edges.push_back({u, v});
    return edges;
}

static void apply_permutation(int n, vector<pair<int, int>>& edges, int& s, int& f, bool permute_sf) {
    vector<int> perm(n + 1);
    for (int i = 1; i <= n; i++) perm[i] = i;
    for (int i = 1; i <= n; i++) {
        int j = rnd.next(i, n);
        swap(perm[i], perm[j]);
    }
    for (auto& e : edges) {
        e.first = perm[e.first];
        e.second = perm[e.second];
        if (e.first == e.second) {
            int a = e.first, b = e.second;
            (void)a; (void)b;
        }
    }
    if (permute_sf) {
        s = perm[s];
        f = perm[f];
        if (s == f) {
            f = (f % n) + 1;
            if (f == s) f = (f % n) + 1;
        }
    }
}

static pair<int, int> pick_hidden_pair_odd_diameter(int n, const vector<pair<int, int>>& edges) {
    vector<vector<int>> g(n + 1);
    for (auto [u, v] : edges) {
        g[u].push_back(v);
        g[v].push_back(u);
    }

    int a = bfs_farthest(n, g, 1).first;

    vector<int> dist(n + 1, -1), par(n + 1, -1);
    queue<int> q;
    dist[a] = 0;
    q.push(a);
    while (!q.empty()) {
        int v = q.front();
        q.pop();
        for (int to : g[v]) {
            if (dist[to] != -1) continue;
            dist[to] = dist[v] + 1;
            par[to] = v;
            q.push(to);
        }
    }
    int b = a;
    for (int i = 1; i <= n; i++) if (dist[i] > dist[b]) b = i;

    vector<int> path;
    for (int v = b; v != -1; v = par[v]) {
        path.push_back(v);
        if (v == a) break;
    }
    int L = (int)path.size() - 1;

    int s = a, f = b;
    if (L >= 2 && (L % 2 == 0)) {
        f = path[1];
        if (f == s) f = b;
    }
    if (s == f) {
        f = (s % n) + 1;
        if (f == s) f = (f % n) + 1;
    }
    return {s, f};
}

int main(int argc, char** argv) {
    registerGen(argc, argv, 1);
    ios::sync_with_stdio(false);
    cin.tie(nullptr);

    string mode = opt<string>("mode", "non");
    int n = opt<int>("n", 1000);
    n = max(2, min(1000, n));
    string shape = opt<string>("shape", "auto");

    long long seedVal = 0;
    if (argc >= 2) seedVal = atoll(argv[1]);

    int t = 1;
    cout << t << "\n";

    vector<pair<int, int>> edges;
    int s = 1, f = 2;

    if (seedVal == 1) {
        n = 2;
        edges = {{1, 2}};
        s = 1; f = 2;
    } else if (seedVal == 2) {
        n = 1000;
        edges = build_star(n, 1);
        s = 2; f = 3;
    } else if (seedVal == 3) {
        n = 1000;
        edges = build_path(n);
        s = 250; f = 750;
    } else {
        if (shape == "auto") {
            int pick = (int)(seedVal % 5);
            if (pick == 0) shape = "binary";
            else if (pick == 1) shape = "broom";
            else if (pick == 2) shape = "prufer";
            else if (pick == 3) shape = "caterpillar";
            else shape = "doublebroom";
        }

        if (shape == "path") {
            edges = build_path(n);
        } else if (shape == "star") {
            edges = build_star(n, 1);
        } else if (shape == "binary") {
            edges = build_binary_heap(n);
        } else if (shape == "broom") {
            int handle_len = rnd.next((int)(n * 7 / 10), (int)(n * 9 / 10));
            edges = build_broom(n, handle_len);
        } else if (shape == "caterpillar") {
            int spine_len = rnd.next((int)(n * 2 / 3), (int)(n * 9 / 10));
            edges = build_caterpillar(n, spine_len);
        } else if (shape == "doublebroom") {
            int path_len = rnd.next((int)(n * 1 / 2), (int)(n * 4 / 5));
            int rem = n - path_len;
            int left_leaves = rem / 2;
            int right_leaves = rem - left_leaves;
            edges = build_double_broom(n, path_len, left_leaves, right_leaves);
        } else {
            edges = build_prufer_tree(n);
        }

        if (mode == "non") {
            auto pr = pick_hidden_pair_odd_diameter(n, edges);
            s = pr.first;
            f = pr.second;
        }

        int dummyS = 1, dummyF = 2;
        apply_permutation(n, edges, dummyS, dummyF, false);
        if (mode == "non") apply_permutation(n, edges, s, f, true);
    }

    cout << n << "\n";
    for (auto [u, v] : edges) cout << u << " " << v << "\n";
    if (mode == "non") {
        cout << s << " " << f << "\n";
    } else if (mode == "adp") {

    } else {
        quitf(_fail, "Unknown --mode (expected non/adp)");
    }

    return 0;
}


This is an interactive problem.

This is the hard version of the problem. The only difference is that $n \le 890$ in this version.

There is a hidden permutation $p$, which is a permutation of $\{1,2,\ldots,n\}$. Let $pos_i$ denote the position of the value $i$ in $p$, i.e., $pos_{p_i} = i$.

To find this permutation, you can ask four types of queries:

* "$1\ m\ i_1\ i_2\ \ldots\ i_m$" ($1 \leq m \leq n$, $i_1,\ i_2,\ \ldots,\ i_m$ must be distinct). Let $k = \min(60, m)$. The jury will return the top $k$ largest number(s) in $[p_{i_1}, p_{i_2}, \ldots, p_{i_m}]$ in increasing order.
* "$2\ m\ i_1\ i_2\ \ldots\ i_m$" ($1 \leq m \leq n$, $i_1,\ i_2,\ \ldots,\ i_m$ must be distinct). Let $k = \min(60, m)$. The jury will return the top $k$ largest number(s) in $[pos_{i_1}, pos_{i_2}, \ldots, pos_{i_m}]$ in increasing order.
* "$3\ m\ i_1\ i_2\ ...\ i_m$" ($1 \leq m \leq n$, $i_1,\ i_2,\ ...,\ i_m$ must be distinct). Let $k = \min(300, m)$. The jury will return the top $k$ largest number(s) in $[p_{i_1}, p_{i_2}, ..., p_{i_m}]$ in increasing order.
* "$4\ m\ i_1\ i_2\ \ldots\ i_m$" ($1 \leq m \leq n$, $i_1,\ i_2,\ \ldots,\ i_m$ must be distinct). Let $k = \min(300, m)$. The jury will return the top $k$ largest number(s) in $[pos_{i_1}, pos_{i_2}, \ldots, pos_{i_m}]$ in increasing order.

Let $c_i$ be the usage count of queries of type $i$ $(1 \le i \le 4)$. Your query count must satisfy the following constraints:

* $c_1+c_2+c_3+c_4 \le 30.$
* $c_3+c_4 \le 1.$

Input

Each test contains multiple test cases. The first line contains the number of test cases $t$ ($1 \le t \le 40$). The description of the test cases follows.

Interaction

The first line of each test case contains one integer $n$ ($2 \le n \le 890$). At this moment, the permutation $p$ is chosen. The interactor in this task is not adaptive. In other words, the permutation $p$ is fixed in every test case and does not change during the interaction.

To ask a query of type $1$, you need to print the line of the following form (without quotes):

* "$1\ m\ i_1\ i_2\ \ldots\ i_m$" ($1 \leq m \leq n$, $i_1, i_2, \ldots, i_m$ must be distinct)

After that, you receive $k=\min(60,m)$ integer(s) — the top $k$ largest number(s) in $[p_{i_1}, p_{i_2}, \ldots, p_{i_m}]$ in increasing order.

To ask a query of type $2$, you need to print the line of the following form (without quotes):

* "$2\ m\ i_1\ i_2\ \ldots\ i_m$" ($1 \leq m \leq n$, $i_1, i_2, \ldots, i_m$ must be distinct)

After that, you receive $k=\min(60,m)$ integer(s) — the top $k$ largest number(s) in $[pos_{i_1}, pos_{i_2}, \ldots, pos_{i_m}]$ in increasing order.

To ask a query of type $3$, you need to print the line of the following form (without quotes):

* "$3\ m\ i_1\ i_2\ \ldots\ i_m$" ($1 \leq m \leq n$, $i_1, i_2, \ldots, i_m$ must be distinct)

After that, you receive $k=\min(300,m)$ integer(s) — the top $k$ largest number(s) in $[p_{i_1}, p_{i_2}, \ldots, p_{i_m}]$ in increasing order.

To ask a query of type $4$, you need to print the line of the following form (without quotes):

* "$4\ m\ i_1\ i_2\ \ldots\ i_m$" ($1 \leq m \leq n$, $i_1, i_2, \ldots, i_m$ must be distinct)

After that, you receive $k=\min(300,m)$ integer(s) — the top $k$ largest number(s) in $[pos_{i_1}, pos_{i_2}, \ldots, pos_{i_m}]$ in increasing order.

Next, if your program has found the permutation $p$, print the line of the following form (without quotes):

* "$!\ p_1\ p_2\ \ldots\ p_n$"

Note that this line is not considered a query and is not taken into account when counting the number of queries asked.

After this, proceed to the next test case.

After printing a query or the answer for a test case, do not forget to output the end of the line and flush the output. Otherwise, you will get the verdict Idleness Limit Exceeded. To do this, use:

* fflush(stdout) or cout.flush() in C++;
* System.out.flush() in Java;
* flush(output) in Pascal;
* stdout.flush() in Python;
* see the documentation for other languages.

Example

Input

```
2
3

2 3

3

2

2
```

Output

```
3 2 3 1

2 1 2

! 3 1 2

4 1 1

! 2 1
```

Note

In the first test case, the hidden permutation is $p = [3, 1, 2]$. Thus, $pos = [2, 3, 1]$.

For the query "3 2 3 1", the jury returns $2$ and $3$ because $2$ and $3$ are the top $k$ largest number(s) in $[p_3, p_1]$, where $k = \min(300, m) = \min(300, 2) = 2$.

For the query "2 1 2", the jury returns $3$ because $3$ is the top $k$ largest number in $[pos_2]$, where $k = \min(60, m) = \min(60, 1) = 1$.

Note that the example is only for understanding the statement and does not guarantee finding the unique permutation $p$.

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

static long long queries = 0;
static long long query_limit = 0;

static void log_metrics() {
    try {
        tout << "queries=" << queries << '\n';
        tout << "query_limit=" << query_limit << '\n';
        tout.flush();
    } catch (...) {

    }
}

static void finish(TResult verdict, const string& msg) {
    log_metrics();
    quitf(verdict, "%s", msg.c_str());
}

static bool readToken(string& s) {
    return (cin >> s) ? true : false;
}

static bool parseLongLongStrict(const string& s, long long& out) {
    if (s.empty()) return false;
    size_t i = 0;
    bool neg = false;
    if (s[0] == '-') {
        neg = true;
        i = 1;
    }
    if (i == s.size()) return false;
    for (; i < s.size(); i++) {
        if (s[i] < '0' || s[i] > '9') return false;
    }
    try {
        size_t pos = 0;
        long long v = stoll(s, &pos, 10);
        if (pos != s.size()) return false;
        out = v;
        return true;
    } catch (...) {
        return false;
    }
}

static long long readIntFromContestantOrDie(const string& what) {
    string tok;
    if (!readToken(tok)) finish(_wa, "unexpected EOF while reading " + what);
    long long v;
    if (!parseLongLongStrict(tok, v)) finish(_pe, "invalid integer token while reading " + what);
    return v;
}

static void printList(const vector<int>& a) {
    for (int i = 0; i < (int)a.size(); i++) {
        if (i) cout << ' ';
        cout << a[i];
    }
    cout << '\n';
    cout.flush();
}

int main(int argc, char** argv) {
    registerInteraction(argc, argv);
    atexit(log_metrics);

    int t;
    try {
        t = inf.readInt(1, 40, "t");
    } catch (...) {
        query_limit = 0;
        log_metrics();
        finish(_pe, "failed to read hidden t");
    }

    query_limit = 30LL * t;
    log_metrics();

    cout << t << '\n';
    cout.flush();

    const long long hard_cap = max(200000LL, 10LL * max(1LL, query_limit));

    for (int tc = 1; tc <= t; tc++) {
        int n;
        try {
            n = inf.readInt(2, 890, "n");
        } catch (...) {
            finish(_pe, "failed to read hidden n");
        }

        vector<int> p(n + 1, 0);
        vector<int> pos(n + 1, 0);
        vector<int> seen(n + 1, 0);

        for (int i = 1; i <= n; i++) {
            int v;
            try {
                v = inf.readInt(1, n, "p_i");
            } catch (...) {
                finish(_pe, "failed to read hidden permutation");
            }
            if (seen[v]++) finish(_pe, "hidden permutation has duplicates");
            p[i] = v;
            pos[v] = i;
        }

        cout << n << '\n';
        cout.flush();

        while (true) {
            string first;
            if (!readToken(first)) finish(_wa, "unexpected EOF (no answer for a test case)");

            if (first == "!") {
                vector<int> ans(n + 1, 0);
                vector<int> used(n + 1, 0);
                for (int i = 1; i <= n; i++) {
                    long long x = readIntFromContestantOrDie("answer permutation");
                    if (x < 1 || x > n) finish(_pe, "answer value out of range");
                    if (used[(int)x]++) finish(_pe, "answer is not a permutation (duplicate)");
                    ans[i] = (int)x;
                }
                for (int i = 1; i <= n; i++) {
                    if (ans[i] != p[i]) finish(_wa, "wrong permutation");
                }
                break;
            }

            long long typLL;
            if (!parseLongLongStrict(first, typLL)) finish(_pe, "invalid query type token");
            if (typLL < 1 || typLL > 4) finish(_pe, "query type out of range");
            int typ = (int)typLL;

            long long mLL = readIntFromContestantOrDie("m");
            if (mLL < 1 || mLL > n) finish(_pe, "m out of range");
            int m = (int)mLL;

            vector<int> idx(m);
            vector<char> used(n + 1, 0);
            for (int i = 0; i < m; i++) {
                long long xLL = readIntFromContestantOrDie("index/value");
                if (xLL < 1 || xLL > n) finish(_pe, "index/value out of range");
                int x = (int)xLL;
                if (used[x]) finish(_pe, "duplicate index/value in a query");
                used[x] = 1;
                idx[i] = x;
            }

            queries++;
            if (queries > hard_cap) finish(_pe, "hard cap exceeded");

            int k = 0;
            if (typ == 1 || typ == 2) k = min(60, m);
            else k = min(300, m);

            vector<int> vals;
            vals.reserve(m);
            if (typ == 1 || typ == 3) {
                for (int x : idx) vals.push_back(p[x]);
            } else {
                for (int x : idx) vals.push_back(pos[x]);
            }

            sort(vals.begin(), vals.end());
            vector<int> out;
            out.reserve(k);
            for (int i = m - k; i < m; i++) out.push_back(vals[i]);

            printList(out);
        }
    }

    finish(_ok, "OK");
    return 0;
}

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

template <class T>
static void shuffleVec(vector<T>& a) {
    for (int i = (int)a.size() - 1; i > 0; --i) {
        int j = rnd.next(0, i);
        swap(a[i], a[j]);
    }
}

static int pickCoprimeStep(int n) {
    if (n <= 2) return 1;
    for (int attempts = 0; attempts < 20000; attempts++) {
        int step = rnd.next(1, n - 1);
        if (std::gcd(step, n) == 1) return step;
    }
    for (int step = 1; step < n; step++) {
        if (std::gcd(step, n) == 1) return step;
    }
    return 1;
}

static vector<int> bitReversalOrder0(int n) {
    int N = 1;
    while (N < n) N <<= 1;
    int lg = 0;
    while ((1 << lg) < N) lg++;

    vector<int> order;
    order.reserve(n);
    for (int x = 0; x < N; x++) {
        int r = 0;
        for (int b = 0; b < lg; b++) {
            if (x & (1 << b)) r |= 1 << (lg - 1 - b);
        }
        if (r < n) order.push_back(r);
    }

    if ((int)order.size() != n) {

        order.clear();
        order.reserve(n);
        for (int i = 0; i < n; i++) order.push_back(i);
    }
    return order;
}

static vector<int> buildCornerMin(int n) {
    vector<int> p(n + 1, 0);
    if (n == 2) {
        p[1] = 2;
        p[2] = 1;
    } else {
        for (int i = 1; i <= n; i++) p[i] = i;
    }
    return p;
}

static vector<int> buildCornerK60(int n) {
    vector<int> p(n + 1, 0);
    int lo = 1, hi = n;
    for (int i = 1; i <= n; i++) {
        if (i & 1) p[i] = hi--;
        else p[i] = lo++;
    }
    return p;
}

static vector<int> buildBitRevAlternating(int n) {
    vector<int> p(n + 1, 0);
    vector<int> ord0 = bitReversalOrder0(n);
    int lo = 1, hi = n;
    for (int i = 0; i < n; i++) {
        int pos = ord0[i] + 1;
        int v = (i % 2 == 0) ? hi-- : lo++;
        p[pos] = v;
    }
    return p;
}

static vector<int> buildSpreadTopStructured(int n, int topCount) {
    topCount = max(1, min(topCount, n));
    vector<int> p(n + 1, 0);

    int step = pickCoprimeStep(n);
    int offset0 = rnd.next(0, n - 1);

    vector<int> seqPos;
    seqPos.reserve(n);
    for (int i = 0; i < n; i++) {
        int pos = (offset0 + (int)((1LL * i * step) % n)) % n;
        seqPos.push_back(pos + 1);
    }

    for (int i = 0; i < topCount; i++) {
        p[seqPos[i]] = n - i;
    }

    int remaining = n - topCount;
    vector<int> vals;
    vals.reserve(remaining);

    int lo = 1, hi = remaining;
    while (lo <= hi) {
        vals.push_back(hi--);
        if (lo <= hi) vals.push_back(lo++);
    }

    int swaps = min(5000, max(0, remaining * 4));
    for (int s = 0; s < swaps; s++) {
        int i = rnd.next(0, remaining - 1);
        int j = rnd.next(0, remaining - 1);
        swap(vals[i], vals[j]);
    }
    int B = rnd.next(5, 13);
    for (int l = 0; l < remaining; l += B) {
        int r = min(remaining, l + B);
        if (rnd.next(0, 1) == 1) reverse(vals.begin() + l, vals.begin() + r);
    }

    for (int i = topCount; i < n; i++) {
        p[seqPos[i]] = vals[i - topCount];
    }

    return p;
}

static void validatePermutationOrDie(const vector<int>& p) {
    int n = (int)p.size() - 1;
    vector<int> seen(n + 1, 0);
    for (int i = 1; i <= n; i++) {
        if (p[i] < 1 || p[i] > n) quitf(_fail, "invalid value");
        if (seen[p[i]]++) quitf(_fail, "duplicate value");
    }
}

int main(int argc, char** argv) {
    registerGen(argc, argv, 1);

    string mode = opt<string>("mode", "non");
    int nOpt = opt<int>("n", -1);
    int topOpt = opt<int>("top", 300);
    string pattern = opt<string>("pattern", "auto");

    if (mode != "non" && mode != "adp") quitf(_fail, "unknown --mode");

    int n;
    int seed = 1;
    if (argc >= 2) {

        bool ok = true;
        for (char c : string(argv[1])) if (!(c == '-' || (c >= '0' && c <= '9'))) ok = false;
        if (ok) {
            try {
                seed = stoi(string(argv[1]));
            } catch (...) {
                seed = 1000000007;
            }
        } else {
            seed = 1000000007;
        }
    }

    if (nOpt != -1) {
        n = nOpt;
    } else if (seed == 1) {
        n = 2;
    } else if (seed == 2) {
        n = 61;
    } else if (seed == 3) {
        n = 890;
    } else {

        int wiggle = rnd.next(0, 40);
        n = 890 - wiggle;
    }

    if (n < 2 || n > 890) quitf(_fail, "n out of bounds");

    cout << 1 << "\n";
    cout << n << "\n";

    if (mode == "adp") {

        return 0;
    }

    vector<int> p;
    if (seed == 1) {
        p = buildCornerMin(n);
    } else if (seed == 2) {
        p = buildCornerK60(n);
    } else if (seed == 3) {
        p = buildBitRevAlternating(n);
    } else {
        if (pattern == "auto") {
            int v = rnd.next(0, 2);
            if (v == 0) pattern = "spread";
            else if (v == 1) pattern = "bitrev";
            else pattern = "rev";
        }

        if (pattern == "spread") {
            int topCount = min(n, max(1, topOpt));
            p = buildSpreadTopStructured(n, topCount);
        } else if (pattern == "bitrev") {
            p = buildBitRevAlternating(n);
        } else if (pattern == "rev") {
            p.assign(n + 1, 0);
            for (int i = 1; i <= n; i++) p[i] = n - i + 1;

            int swaps = min(2000, n * 2);
            for (int s = 0; s < swaps; s++) {
                int i = rnd.next(1, n);
                int j = rnd.next(1, n);
                swap(p[i], p[j]);
            }
        } else {

            int topCount = min(n, max(1, topOpt));
            p = buildSpreadTopStructured(n, topCount);
        }
    }

    validatePermutationOrDie(p);

    for (int i = 1; i <= n; i++) {
        if (i > 1) cout << ' ';
        cout << p[i];
    }
    cout << "\n";
    return 0;
}


This is an interactive problem.

There is a secret permutation $p$ of $[0,1,2,\ldots,n-1]$. Your task is to find $2$ indices $x$ and $y$ ($1 \leq x, y \leq n$, possibly $x=y$) such that $p_x=0$ or $p_y=0$. In order to find it, you are allowed to ask at most $2n$ queries.

In one query, you give two integers $i$ and $j$ ($1 \leq i, j \leq n$, $i \neq j$) and receive the value of $\gcd(p_i,p_j)^\dagger$.

Note that the permutation $p$ is fixed before any queries are made and does not depend on the queries.

$^\dagger$ $\gcd(x, y)$ denotes the greatest common divisor (GCD) of integers $x$ and $y$. Note that $\gcd(x,0)=\gcd(0,x)=x$ for all positive integers $x$.

Input

Each test contains multiple test cases. The first line contains the number of test cases $t$ ($1 \leq t \leq 10^4$). The description of the test cases follows.

The first line of each test case contains a single integer $n$ ($2 \leq n \leq 2 \cdot 10^4$).

After reading the integer $n$ for each test case, you should begin the interaction.

It is guaranteed that the sum of $n$ over all test cases does not exceed $2 \cdot 10^4$.

Interaction

The interaction for each test case begins by reading the integer $n$.

To make a query, output "? $i$ $j$" ($1 \leq i, j \leq n$, $i \neq j$) without quotes. Afterwards, you should read a single integer — the answer to your query $\gcd(p_i,p_j)$. You can make at most $2n$ such queries in each test case.

If you want to print the answer, output "! $x$ $y$" ($1 \leq x, y \leq n$) without quotes. After doing that, read $1$ or $-1$. If $p_x=0$ or $p_y=0$, you'll receive $1$, otherwise you'll receive $-1$. If you receive $-1$, your program must terminate immediately to receive a Wrong Answer verdict. Otherwise, you can get an arbitrary verdict because your solution will continue to read from a closed stream.

If you receive the integer $-1$ instead of an answer or a valid value of $n$, it means your program has made an invalid query, has exceeded the limit of queries, or has given an incorrect answer on the previous test case. Your program must terminate immediately to receive a Wrong Answer verdict. Otherwise, you can get an arbitrary verdict because your solution will continue to read from a closed stream.

After printing a query or the answer, do not forget to output the end of line and flush the output. Otherwise, you will get Idleness limit exceeded. To do this, use:

* fflush(stdout) or cout.flush() in C++;
* System.out.flush() in Java;
* flush(output) in Pascal;
* stdout.flush() in Python;
* see documentation for other languages.

Example

Input

```
2
2

1

1
5

2

4

1
```

Output

```? 1 2! 1 2? 1 2? 2 3! 3 3
```

Note

In the first test, the interaction proceeds as follows.

|  |  |  |
| --- | --- | --- |
| Solution | Jury | Explanation |
|  | $\texttt{2}$ | There are 2 test cases. |
|  | $\texttt{2}$ | In the first test case, the hidden permutation is $[1,0]$, with length $2$. |
| $\texttt{? 1 2}$ | $\texttt{1}$ | The solution requests $\gcd(p_1,p_2)$, and the jury responds with $1$. |
| $\texttt{! 1 2}$ | $\texttt{1}$ | The solution knows that either $p_1=0$ or $p_2=0$, and prints the answer. Since the output is correct, the jury responds with $1$ and continues to the next test case. |
|  | $\texttt{5}$ | In the second test case, the hidden permutation is $[2,4,0,1,3]$, with length $5$. |
| $\texttt{? 1 2}$ | $\texttt{2}$ | The solution requests $\gcd(p_1,p_2)$, and the jury responds with $2$. |
| $\texttt{? 2 3}$ | $\texttt{4}$ | The solution requests $\gcd(p_2,p_3)$, and the jury responds with $4$. |
| $\texttt{! 3 3}$ | $\texttt{1}$ | The solution has somehow determined that $p_3=0$, and prints the answer. Since the output is correct, the jury responds with $1$. |

Note that the empty lines in the example input and output are for the sake of clarity, and do not occur in the real interaction.

After each test case, make sure to read $1$ or $-1$.

#include "testlib.h"
#include <bits/stdc++.h>

using namespace std;

static long long queries = 0;
static long long query_limit = 0;

void log_metrics() {
    try {
        tout << "queries=" << queries << endl;
        tout << "query_limit=" << query_limit << endl;
    } catch (...) {}
}

void finish(TResult verdict, const string& msg) {
    log_metrics();
    quitf(verdict, "%s", msg.c_str());
}

long long gcd_val(long long a, long long b) {
    while (b) {
        a %= b;
        swap(a, b);
    }
    return a;
}

int main(int argc, char* argv[]) {

    registerInteraction(argc, argv);

    atexit(log_metrics);

    int t = inf.readInt();

    cout << t << endl;

    for (int k = 0; k < t; ++k) {

        int n = inf.readInt();

        vector<int> p(n);
        for (int i = 0; i < n; ++i) {
            p[i] = inf.readInt();
        }

        long long limit_this_case = 2LL * n;
        query_limit += limit_this_case;

        log_metrics();

        cout << n << endl;

        int queries_this_case = 0;
        bool case_solved = false;

        while (true) {
            string token;
            if (!(cin >> token)) {

                finish(_wa, "Unexpected EOF reading token from solution");
            }

            if (token == "!") {

                int x, y;
                if (!(cin >> x >> y)) {
                    finish(_wa, "Unexpected EOF reading answer indices");
                }

                if (x < 1 || x > n || y < 1 || y > n) {
                    cout << -1 << endl;
                    finish(_wa, format("Answer indices %d %d out of range [1, %d]", x, y, n));
                }

                if (p[x - 1] == 0 || p[y - 1] == 0) {
                    cout << 1 << endl;
                    case_solved = true;
                    break;
                } else {
                    cout << -1 << endl;
                    finish(_wa, format("Incorrect answer: p[%d]=%d, p[%d]=%d, neither is 0", x, p[x-1], y, p[y-1]));
                }

            } else {

                int u, v;
                if (token == "?") {
                    if (!(cin >> u >> v)) {
                        finish(_wa, "Unexpected EOF reading query indices");
                    }
                } else {

                    try {
                        u = stoi(token);
                    } catch (...) {
                        cout << -1 << endl;
                        finish(_wa, "Invalid token '" + token + "' (expected '?', '!', or integer)");
                    }
                    if (!(cin >> v)) {
                        finish(_wa, "Unexpected EOF reading second query index");
                    }
                }

                queries++;
                queries_this_case++;
                log_metrics();

                if (queries_this_case > limit_this_case) {
                    cout << -1 << endl;
                    finish(_wa, format("Query limit exceeded for this test case (%d > %lld)", queries_this_case, limit_this_case));
                }

                if (u < 1 || u > n || v < 1 || v > n) {
                    cout << -1 << endl;
                    finish(_wa, format("Query indices %d %d out of range [1, %d]", u, v, n));
                }
                if (u == v) {
                    cout << -1 << endl;
                    finish(_wa, format("Query indices must be distinct (%d == %d)", u, v));
                }

                long long res = gcd_val(p[u - 1], p[v - 1]);
                cout << res << endl;
            }
        }

        if (!case_solved) {

             finish(_wa, "Internal logic error: loop exited without solving");
        }
    }

    finish(_ok, "All test cases passed");
    return 0;
}

#include "testlib.h"
#include <bits/stdc++.h>

using namespace std;

static long long total_queries = 0;
static long long global_query_limit = 0;

static void log_metrics() {
    try {
        tout << "queries=" << total_queries << endl;
        tout << "query_limit=" << global_query_limit << endl;
    } catch (...) {}
}

static void finish(TResult verdict, const string& msg) {
    log_metrics();
    quitf(verdict, "%s", msg.c_str());
}

struct TestCase {
    int n;
    long long limit;
    vector<int> p;
};

int main(int argc, char** argv) {

    registerInteraction(argc, argv);

    atexit(log_metrics);

    int t = inf.readInt();

    vector<int> tokens;
    while (!inf.seekEof()) {
        tokens.push_back(inf.readInt());
    }

    vector<TestCase> cases;
    size_t cursor = 0;

    mt19937 rng(5489331);

    for (int i = 0; i < t; ++i) {
        if (cursor >= tokens.size()) {
            finish(_fail, "Unexpected end of input (missing n)");
        }
        int n = tokens[cursor++];
        if (n < 2) finish(_fail, "Invalid n < 2 in input");

        TestCase tc;
        tc.n = n;
        tc.limit = 2LL * n;

        bool has_p = false;
        if (cursor + n <= tokens.size()) {
            vector<bool> present(n, false);
            bool possible = true;
            for (int k = 0; k < n; ++k) {
                int val = tokens[cursor + k];
                if (val < 0 || val >= n || present[val]) {
                    possible = false;
                    break;
                }
                present[val] = true;
            }

            if (possible) {

                tc.p.resize(n);
                for (int k = 0; k < n; ++k) {
                    tc.p[k] = tokens[cursor + k];
                }
                cursor += n;
                has_p = true;
            }
        }

        if (!has_p) {

            tc.p.resize(n);
            iota(tc.p.begin(), tc.p.end(), 0);
            shuffle(tc.p.begin(), tc.p.end(), rng);
        }

        cases.push_back(tc);
        global_query_limit += tc.limit;
    }

    log_metrics();

    cout << t << endl;

    for (int i = 0; i < t; ++i) {
        const auto& tc = cases[i];

        cout << tc.n << endl;

        int queries_spent = 0;
        bool active = true;

        while (active) {
            string kind;
            if (!(cin >> kind)) {
                finish(_wa, "Solution exited prematurely (EOF on stdin)");
            }

            if (kind == "?") {
                int u, v;
                if (!(cin >> u >> v)) {
                    finish(_wa, "Invalid query format");
                }

                if (u < 1 || u > tc.n || v < 1 || v > tc.n || u == v) {
                    cout << -1 << endl;
                    finish(_wa, "Invalid query parameters (indices out of range or equal)");
                }

                queries_spent++;
                total_queries++;

                if (total_queries % 100 == 0) log_metrics();

                if (queries_spent > tc.limit) {
                    cout << -1 << endl;
                    finish(_wa, "Query limit exceeded for this test case");
                }

                int res = std::gcd(tc.p[u-1], tc.p[v-1]);
                cout << res << endl;

            } else if (kind == "!") {
                int x, y;
                if (!(cin >> x >> y)) {
                    finish(_wa, "Invalid answer format");
                }

                if (x < 1 || x > tc.n || y < 1 || y > tc.n) {
                    cout << -1 << endl;
                    finish(_wa, "Invalid answer parameters");
                }

                bool correct = (tc.p[x-1] == 0 || tc.p[y-1] == 0);
                if (correct) {
                    cout << 1 << endl;
                    active = false;
                } else {
                    cout << -1 << endl;
                    finish(_wa, "Incorrect answer: neither index contains 0");
                }

            } else {
                finish(_wa, "Invalid command (expected '?' or '!')");
            }
        }
    }

    finish(_ok, "All cases passed");
    return 0;
}

#include "testlib.h"
#include <bits/stdc++.h>

using namespace std;

int main(int argc, char* argv[]) {
    registerGen(argc, argv, 1);

    string mode = opt<string>("mode", "non");
    int sum_n_limit = opt<int>("maxn", 20000);
    int t_arg = opt<int>("t", -1);
    int n_arg = opt<int>("n", -1);

    if (sum_n_limit < 2) sum_n_limit = 2;

    long long seed_val = -1;
    string seed_str = argv[1];
    try {
        size_t pos;
        seed_val = stoll(seed_str, &pos);
        if (pos != seed_str.size()) seed_val = -1;
    } catch (...) {
        seed_val = -1;
    }

    vector<int> ns;

    if (t_arg != -1) {
        if (n_arg != -1) {

            if (sum_n_limit < (long long)t_arg * n_arg) {

            }
            for (int i = 0; i < t_arg; ++i) ns.push_back(n_arg);
        } else {

            if (sum_n_limit < 2 * t_arg) sum_n_limit = 2 * t_arg;
            ns = rnd.partition(t_arg, sum_n_limit, 2);
        }
    } else if (n_arg != -1) {

        if (n_arg < 2) n_arg = 2;
        int t = sum_n_limit / n_arg;
        if (t < 1) t = 1;
        if (t > 10000) t = 10000;
        for (int i = 0; i < t; ++i) ns.push_back(n_arg);
    } else {

        if (seed_val == 1) {

            ns.push_back(sum_n_limit);
        } else if (seed_val == 2) {

            int t = sum_n_limit / 2;
            if (t > 10000) t = 10000;
            for (int i = 0; i < t; ++i) ns.push_back(2);
        } else if (seed_val == 3) {

            int t = 50;
            if (t * 2 > sum_n_limit) t = sum_n_limit / 2;
            ns = rnd.partition(t, sum_n_limit, 2);
        } else {

            int type = rnd.next(3);
            int t;
            if (type == 0) t = rnd.next(1, 5);
            else if (type == 1) t = rnd.next(10, 100);
            else t = rnd.next(100, min(2000, sum_n_limit / 2));

            if (t < 1) t = 1;
            ns = rnd.partition(t, sum_n_limit, 2);
        }
    }

    cout << ns.size() << endl;

    for (int n : ns) {
        cout << n;
        if (mode == "adp") {

            cout << endl;
        } else {

            cout << endl;
            vector<int> p(n);
            iota(p.begin(), p.end(), 0);

            int pattern = rnd.next(100);

            if (seed_val == 3) pattern = (rnd.next(2) ? 80 : 90);

            if (pattern < 70) {

                shuffle(p.begin(), p.end());
            } else if (pattern < 80) {

                swap(p[0], p[rnd.next(n)]);
                int noise = rnd.next(0, 3);
                for (int k = 0; k < noise; ++k)
                    swap(p[rnd.next(n)], p[rnd.next(n)]);
            } else if (pattern < 90) {

                int k = rnd.next(1, n - 1);
                for (int i = 0; i < n; ++i) p[i] = (i + k) % n;
            } else {

                shuffle(p.begin(), p.end());
                int pos0 = -1, pos1 = -1;
                for (int i = 0; i < n; ++i) {
                    if (p[i] == 0) pos0 = i;
                    if (p[i] == 1) pos1 = i;
                }
                int target = (pos0 + 1) % n;
                if (target != pos1) {
                    iter_swap(p.begin() + target, p.begin() + pos1);
                }
            }

            for (int i = 0; i < n; ++i) {
                cout << p[i] << (i == n - 1 ? "" : " ");
            }
            cout << endl;
        }
    }

    return 0;
}


The minus operator on binary values $a$ and $b$ is defined by $( a - b ) = 1$ if $a = 1$ and $b = 0$ ; otherwise, $( a - b ) = 0$ . Also, the syntax of an expression is defined as follows. Here, $_ \textrm { x }$ , parentheses, and the minus are terminal symbols, and $E$ is the start symbol.

$$
E : = \textbf { x } \mid \mathbf { \Omega } ( E - E )
$$

The judge program possesses an expression adhering to $E$ . The expression is hidden from you. At the start, you are only provided with the number of terminal symbols $_ \textrm { x }$ in the expression, denoted by $n$ .

Your task is to guess the expression by making a limited number of queries.

In a single query, you specify a binary string $S$ of length $n$ . The judge program then temporarily replaces each occurrence of the $i$ -th terminal symbol $_ \textrm { x }$ from the left with $S _ { i }$ , for $i = 1 , \ldots , n$ , and evaluates the replaced expression based on the definition of the minus operator. After that, the judge program returns the evaluated value to you, which is either 0 or 1.

# Interaction

The first line of input contains an integer $n$ $3 \leq n \leq 2 0 0$ ). After reading the integer, your program can start making queries. For each query, your program should write a line of the form “query $S ^ { \ast }$ . Here, $S$ is a binary string of length $n$ . Each character of $S$ must be either 0 or 1. In response, an input line containing the evaluated value becomes available.

Your program can make up to 500 queries. If your program makes more than 500 queries, it will be judged as “Wrong Answer.”

When your program identifies the expression that the judge program possesses, it should write a line of the form “answer $T ^  \ast \}$ , where $T$ is the expression. After that, the interaction stops and your program should terminate.

Under the constraints above, it can be shown that the expression can be uniquely identified.

Notes on interactive judging:

• The evaluation is non-adversarial, meaning that the expression is chosen in advance rather than in response to your queries.
• Do not forget to flush output buffers after writing. See the “Judging Details” document for details.
• You are provided with a command-line tool for local testing, together with input files corresponding to the sample interactions. You can download these files from DOMjudge. The tool has comments at the top to explain its use.

# The 2025 ICPC Asia Pacific Championship

Hosted by the National University of Singapore

# Sample Interaction #1

Explanation for the sample interaction #1

When $n = 3$ , there are only two possible expressions: $( \mathbf { \partial } ( \mathbf { \partial } \mathbf { x } - \mathbf { x } ) - \mathbf { x } )$ or $\left( \mathbf { X } ^ { - } \left( \mathbf { X } ^ { - } \mathbf { X } \right) \ \right)$ . For a query $s = 1 1 1$ , the evaluated values for these expressions are,

In this example, the judge program returns 0, indicating that the first expression is the correct one.

![](images/c57d081e93e955b0624e5137ab7ccd5cea9c764332415d30afb1aa8a14d19ca3.jpg)

#include "testlib.h"
#include <bits/stdc++.h>

using namespace std;

static long long queries = 0;

static long long query_limit = 500;
static const long long hard_cap = 20000;

static void log_metrics() {
    try {
        tout << "queries=" << queries << endl;
        tout << "query_limit=" << query_limit << endl;
    } catch (...) {

    }
}

static void finish(TResult verdict, const string& msg) {
    log_metrics();
    quitf(verdict, "%s", msg.c_str());
}

struct Node {
    bool is_leaf;
    int leaf_idx;
    Node *left = nullptr;
    Node *right = nullptr;

    Node(int idx) : is_leaf(true), leaf_idx(idx) {}
    Node(Node* l, Node* r) : is_leaf(false), leaf_idx(-1), left(l), right(r) {}

    ~Node() {
        if (left) delete left;
        if (right) delete right;
    }
};

string hidden_expr_str;
int parse_pos = 0;
int leaf_counter = 0;

Node* parse_expression() {
    if (parse_pos >= (int)hidden_expr_str.length()) {
        quitf(_fail, "Unexpected end of hidden expression during parsing");
    }

    if (hidden_expr_str[parse_pos] == 'x') {
        parse_pos++;
        return new Node(leaf_counter++);
    } else if (hidden_expr_str[parse_pos] == '(') {
        parse_pos++;
        Node* left = parse_expression();

        if (parse_pos >= (int)hidden_expr_str.length() || hidden_expr_str[parse_pos] != '-') {
            quitf(_fail, "Invalid expression format: expected '-' at pos %d", parse_pos);
        }
        parse_pos++;

        Node* right = parse_expression();

        if (parse_pos >= (int)hidden_expr_str.length() || hidden_expr_str[parse_pos] != ')') {
            quitf(_fail, "Invalid expression format: expected ')' at pos %d", parse_pos);
        }
        parse_pos++;

        return new Node(left, right);
    } else {
        quitf(_fail, "Invalid character '%c' in expression at pos %d", hidden_expr_str[parse_pos], parse_pos);
        return nullptr;
    }
}

int evaluate(Node* node, const string& S) {
    if (node->is_leaf) {

        return (S[node->leaf_idx] == '1' ? 1 : 0);
    } else {
        int l = evaluate(node->left, S);
        int r = evaluate(node->right, S);
        if (l == 1 && r == 0) return 1;
        else return 0;
    }
}

string clean_string(const string& s) {
    string res;
    for (char c : s) {
        if (!isspace((unsigned char)c)) res += c;
    }
    return res;
}

int main(int argc, char** argv) {

    registerInteraction(argc, argv);
    atexit(log_metrics);

    int n = inf.readInt();
    hidden_expr_str = inf.readToken();

    leaf_counter = 0;
    parse_pos = 0;
    Node* root = parse_expression();

    if (leaf_counter != n) {
        quitf(_fail, "Parsed leaf count (%d) does not match N (%d) in hidden input", leaf_counter, n);
    }
    if (parse_pos != (int)hidden_expr_str.length()) {
        quitf(_fail, "Extra characters found after parsing hidden expression");
    }

    cout << n << endl;

    while (true) {

        if (queries > hard_cap) {
            finish(_pe, "Hard query limit exceeded (anti-spam)");
        }

        string token;
        if (!(cin >> token)) {

            finish(_wa, "Unexpected EOF (solution terminated without providing answer)");
        }

        bool is_query = false;
        bool is_answer = false;
        string payload = "";

        if (token == "query" || token == "?") {
            is_query = true;
            if (!(cin >> payload)) finish(_wa, "EOF after query command");
        }
        else if (token == "answer" || token == "!") {
            is_answer = true;
            string line;
            getline(cin, line);
            payload = line;
        }
        else if (token.size() > 1 && token[0] == '?') {
            is_query = true;
            payload = token.substr(1);
        }
        else if (token.size() > 1 && token[0] == '!') {
            is_answer = true;
            string line;
            getline(cin, line);
            payload = token.substr(1) + line;
        }
        else if (token.find("answer") == 0) {
            is_answer = true;
            string line;
            getline(cin, line);
            payload = token.substr(6) + line;
        }
        else {
            finish(_wa, "Invalid command token: " + token);
        }

        if (is_query) {
            queries++;

            if (queries % 10 == 0) log_metrics();

            if (queries > query_limit) {
                finish(_wa, "Query limit exceeded (> " + to_string(query_limit) + ")");
            }

            if ((int)payload.length() != n) {
                finish(_wa, "Query string length must be " + to_string(n) + ", got " + to_string(payload.length()));
            }
            for (char c : payload) {
                if (c != '0' && c != '1') {
                    finish(_wa, "Query string must contain only '0' and '1'");
                }
            }

            int res = evaluate(root, payload);
            cout << res << endl;

        } else if (is_answer) {

            string user_clean = clean_string(payload);
            string hidden_clean = clean_string(hidden_expr_str);

            if (user_clean == hidden_clean) {
                finish(_ok, "Correct expression identified");
            } else {
                finish(_wa, "Incorrect expression. Expected: " + hidden_clean + ", Got: " + user_clean);
            }
        }
    }

    delete root;
    return 0;
}

#include "testlib.h"
#include <bits/stdc++.h>

using namespace std;

double cat[205];
bool cat_computed = false;

void precompute_cat() {
    if (cat_computed) return;
    cat[0] = 1.0;

    for (int i = 1; i <= 200; ++i) {
        cat[i] = 0;
        for (int j = 0; j < i; ++j) {
            cat[i] += cat[j] * cat[i - 1 - j];
        }
    }
    cat_computed = true;
}

string gen_catalan(int n) {
    if (n == 1) return "x";
    precompute_cat();

    double total_ways = cat[n - 1];
    double r = rnd.next() * total_ways;

    int k = -1;
    double current_sum = 0;

    for (int i = 1; i < n; ++i) {
        double ways = cat[i - 1] * cat[n - i - 1];
        if (current_sum + ways >= r) {
            k = i;
            break;
        }
        current_sum += ways;
    }
    if (k == -1) k = n - 1;

    return "(" + gen_catalan(k) + "-" + gen_catalan(n - k) + ")";
}

string gen_bst(int n) {
    if (n == 1) return "x";
    int k = rnd.next(1, n - 1);
    return "(" + gen_bst(k) + "-" + gen_bst(n - k) + ")";
}

string gen_skewed(int n, int dir) {
    if (n == 1) return "x";
    int k;
    if (dir == 0) k = n - 1;
    else k = 1;
    return "(" + gen_skewed(k, dir) + "-" + gen_skewed(n - k, dir) + ")";
}

string gen_zigzag(int n, bool left) {
    if (n == 1) return "x";
    int k = left ? (n - 1) : 1;
    return "(" + gen_zigzag(k, !left) + "-" + gen_zigzag(n - k, !left) + ")";
}

int main(int argc, char* argv[]) {
    registerGen(argc, argv, 1);

    string mode = opt<string>("mode", "non");
    int n_arg = opt<int>("n", 0);

    int n = n_arg;
    int seed_idx = atoi(argv[1]);

    if (n == 0) {
        if (seed_idx == 1) n = 3;
        else if (seed_idx == 2) n = 200;
        else if (seed_idx == 3) n = 199;
        else if (seed_idx == 4) n = 10;
        else if (seed_idx == 5) n = 50;
        else if (seed_idx == 6) n = 100;
        else n = rnd.next(3, 200);
    }

    string expr;

    if (seed_idx == 1) {

        expr = gen_catalan(n);
    } else if (seed_idx == 2) {

        expr = gen_skewed(n, 1);
    } else if (seed_idx == 3) {

        expr = gen_skewed(n, 0);
    } else if (seed_idx == 4) {

        expr = gen_zigzag(n, true);
    } else if (seed_idx == 5) {

        expr = gen_bst(n);
    } else if (seed_idx == 6) {

        expr = gen_catalan(n);
    } else {

        int type = rnd.next(100);
        if (type < 40) expr = gen_catalan(n);
        else if (type < 70) expr = gen_bst(n);
        else if (type < 85) expr = gen_skewed(n, 0);
        else expr = gen_skewed(n, 1);
    }

    if (mode == "adp") {

        println(n);
    } else {

        println(n);
        println(expr);
    }

    return 0;
}


This is an interactive problem.

Ayush devised yet another scheme to set the password of his lock. The lock has $n$ slots where each slot can hold any non-negative integer. The password $P$ is a sequence of $n$ integers, $i$-th element of which goes into the $i$-th slot of the lock.

To set the password, Ayush comes up with an array $A$ of $n$ integers each in the range $[0, 2^{63}-1]$. He then sets the $i$-th element of $P$ as the bitwise OR of all integers in the array except $A_i$.

You need to guess the password. To make a query, you can choose a non-empty subset of indices of the array and ask the bitwise OR all elements of the array with index in this subset. You can ask no more than 13 queries.

Input

The first line of input contains one integer $n$ $(2 \le n \le 1000)$ — the number of slots in the lock.

Interaction

To ask a query print a single line:

* In the beginning print "? c " (without quotes) where $c$ $(1 \leq c \leq n)$ denotes the size of the subset of indices being queried, followed by $c$ distinct space-separated integers in the range $[1, n]$.

For each query, you will receive an integer $x$ — the bitwise OR of values in the array among all the indices queried. If the subset of indices queried is invalid or you exceeded the number of queries then you will get $x = -1$. In this case, you should terminate the program immediately.

When you have guessed the password, print a single line "! " (without quotes), followed by $n$ space-separated integers  — the password sequence.

Guessing the password does not count towards the number of queries asked.

The interactor is not adaptive. The array $A$ does not change with queries.

After printing a query do not forget to output the end of the line and flush the output. Otherwise, you will get Idleness limit exceeded. To do this, use:

* fflush(stdout) or cout.flush() in C++;
* System.out.flush() in Java;
* flush(output) in Pascal;
* stdout.flush() in Python;
* see the documentation for other languages.

Example

Input

```
3

1

2

4
```

Output

```? 1 1? 1 2? 1 3! 6 5 3
```

Note

The array $A$ in the example is $\{{1, 2, 4\}}$. The first element of the password is bitwise OR of $A_2$ and $A_3$, the second element is bitwise OR of $A_1$ and $A_3$ and the third element is bitwise OR of $A_1$ and $A_2$. Hence the password sequence is $\{{6, 5, 3\}}$.

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

static long long queries = 0;
static long long query_limit = 0;

static void log_metrics() {
    try {
        tout << "queries=" << queries << "\n";
        tout << "query_limit=" << query_limit << "\n";
        tout.flush();
    } catch (...) {

    }
}

static void finish(TResult verdict, const string& msg) {
    log_metrics();
    quitf(verdict, "%s", msg.c_str());
}

static bool parseLongLongToken(const string& s, long long& out) {
    if (s.empty()) return false;
    int i = 0;
    bool neg = false;
    if (s[i] == '-') {
        neg = true;
        i++;
        if (i == (int)s.size()) return false;
    }
    if (s[i] < '0' || s[i] > '9') return false;
    __int128 val = 0;
    for (; i < (int)s.size(); i++) {
        char c = s[i];
        if (c < '0' || c > '9') return false;
        val = val * 10 + (c - '0');
        if (!neg && val > (__int128)LLONG_MAX) return false;
        if (neg && -val < (__int128)LLONG_MIN) return false;
    }
    out = neg ? (long long)(-val) : (long long)val;
    return true;
}

static long long readLLFromCinOrDie(const string& what) {
    string tok;
    if (!(cin >> tok)) finish(_pe, "Unexpected EOF while reading " + what);
    long long v;
    if (!parseLongLongToken(tok, v)) finish(_pe, "Malformed integer token for " + what);
    return v;
}

int main(int argc, char** argv) {
    registerInteraction(argc, argv);
    atexit(log_metrics);

    try {
        int n = inf.readInt(2, 1000, "n");
        vector<unsigned long long> a(n);
        for (int i = 0; i < n; i++) {
            long long x = inf.readLong(0LL, LLONG_MAX, "a[i]");
            a[i] = (unsigned long long)x;
        }

        query_limit = 13;

        log_metrics();

        cout << n << endl;

        vector<unsigned long long> pref(n + 1, 0), suff(n + 1, 0);
        for (int i = 0; i < n; i++) pref[i + 1] = pref[i] | a[i];
        for (int i = n - 1; i >= 0; i--) suff[i] = suff[i + 1] | a[i];
        vector<unsigned long long> expected(n);
        for (int i = 0; i < n; i++) expected[i] = pref[i] | suff[i + 1];

        long long hard_cap = max(200000LL, 10LL * query_limit);

        vector<int> seen(n, 0);
        int stamp = 0;

        while (true) {
            string cmd;
            if (!(cin >> cmd)) finish(_pe, "Unexpected EOF (no final answer)");

            if (cmd == "?") {
                long long c_ll = readLLFromCinOrDie("c");
                if (c_ll < 1 || c_ll > n) {
                    cout << -1 << endl;
                    finish(_pe, "Invalid subset size c");
                }
                int c = (int)c_ll;

                queries++;
                if (queries > hard_cap) finish(_pe, "Hard cap exceeded");

                stamp++;
                unsigned long long res = 0;

                for (int j = 0; j < c; j++) {
                    long long idx_ll = readLLFromCinOrDie("index");
                    if (idx_ll < 1 || idx_ll > n) {
                        cout << -1 << endl;
                        finish(_pe, "Index out of range");
                    }
                    int idx = (int)idx_ll - 1;
                    if (seen[idx] == stamp) {
                        cout << -1 << endl;
                        finish(_pe, "Duplicate index in subset");
                    }
                    seen[idx] = stamp;
                    res |= a[idx];
                }

                cout << (unsigned long long)res << endl;
            } else if (cmd == "!") {
                vector<unsigned long long> got(n);
                for (int i = 0; i < n; i++) {
                    long long v = readLLFromCinOrDie("answer[i]");
                    if (v < 0) finish(_wa, "Negative value in final answer");
                    got[i] = (unsigned long long)v;
                }

                for (int i = 0; i < n; i++) {
                    if (got[i] != expected[i]) {
                        finish(_wa, "Wrong answer");
                    }
                }
                finish(_ok, "OK");
            } else {
                finish(_pe, "Unknown command token");
            }
        }
    } catch (const std::exception& e) {
        finish(_pe, string("Exception: ") + e.what());
    } catch (...) {
        finish(_pe, "Unknown exception");
    }
    return 0;
}

#include "testlib.h"
#include <bits/stdc++.h>
using namespace std;

static long long FULL63() {
    long long x = (1LL << 62) - 1;
    x |= (1LL << 62);
    return x;
}

int main(int argc, char** argv) {
    registerGen(argc, argv, 1);

    string mode = opt<string>("mode", "non");
    long long seed = 0;
    if (argc >= 2) seed = atoll(argv[1]);

    int minn = opt<int>("minn", 2);
    int maxn = opt<int>("maxn", 1000);
    int nOpt = opt<int>("n", -1);
    int hard = opt<int>("hard", 1);

    minn = max(minn, 2);
    maxn = min(maxn, 1000);
    if (minn > maxn) minn = maxn;

    int n = -1;
    if (nOpt != -1) {
        n = nOpt;
    } else {
        if (seed == 1) n = 2;
        else if (seed == 2) n = 1000;
        else if (seed == 3) n = 1000;
        else {
            if (hard) n = maxn;
            else n = rnd.next(minn, maxn);
        }
    }
    n = max(minn, min(maxn, n));

    if (mode == "adp") {
        cout << n << "\n";
        return 0;
    }

    const long long FULL = FULL63();
    vector<long long> a(n, 0);

    if (seed == 1) {
        n = 2;
        a.assign(n, 0);
        a[0] = 0;
        a[1] = FULL;
        cout << n << "\n" << a[0] << " " << a[1] << "\n";
        return 0;
    }
    if (seed == 2) {
        n = 1000;
        a.assign(n, 0);
        cout << n << "\n";
        for (int i = 0; i < n; i++) {
            if (i) cout << ' ';
            cout << 0;
        }
        cout << "\n";
        return 0;
    }
    if (seed == 3) {
        n = 1000;
        a.assign(n, 0);
        int m = min(63, n);
        for (int i = 0; i < m; i++) a[i] = (1LL << i);
        cout << n << "\n";
        for (int i = 0; i < n; i++) {
            if (i) cout << ' ';
            cout << a[i];
        }
        cout << "\n";
        return 0;
    }

    vector<int> bits(63);
    iota(bits.begin(), bits.end(), 0);
    for (int i = 0; i < 63; i++) {
        int j = rnd.next(i, 62);
        swap(bits[i], bits[j]);
    }

    int commonLo = hard ? 45 : 30;
    int commonHi = hard ? 58 : 50;
    commonLo = max(0, min(63, commonLo));
    commonHi = max(0, min(63, commonHi));
    if (commonLo > commonHi) swap(commonLo, commonHi);
    int commonCnt = rnd.next(commonLo, commonHi);

    long long commonMask = 0;
    for (int i = 0; i < commonCnt; i++) commonMask |= (1LL << bits[i]);

    int rem = 63 - commonCnt;
    int rareCnt = 0;
    if (rem > 0) {
        int rareLo = hard ? 6 : 3;
        int rareHi = hard ? min(14, rem) : min(10, rem);
        rareLo = max(0, min(rem, rareLo));
        rareHi = max(0, min(rem, rareHi));
        if (rareLo > rareHi) swap(rareLo, rareHi);
        rareCnt = rnd.next(rareLo, rareHi);
    }

    vector<int> rareBits;
    for (int i = 0; i < rareCnt; i++) rareBits.push_back(bits[commonCnt + i]);

    vector<int> patternBits;
    for (int i = commonCnt + rareCnt; i < 63; i++) patternBits.push_back(bits[i]);

    vector<long long> extra(n, 0);

    for (int b : rareBits) {
        int pos1 = rnd.next(0, n - 1);
        extra[pos1] |= (1LL << b);
        if (n >= 2 && rnd.next(0, 9) < 3) {
            int pos2 = rnd.next(0, n - 1);
            while (pos2 == pos1) pos2 = rnd.next(0, n - 1);
            extra[pos2] |= (1LL << b);
        }
    }

    int usePattern = 0;
    if (!patternBits.empty()) {
        int lo = hard ? 10 : 6;
        int hi = hard ? 16 : 12;
        lo = min(lo, (int)patternBits.size());
        hi = min(hi, (int)patternBits.size());
        if (lo > hi) lo = hi;
        usePattern = (hi == 0 ? 0 : rnd.next(lo, hi));
    }
    for (int t = 0; t < usePattern; t++) {
        int b = patternBits[t];
        int maxP = min(n, hard ? 200 : 80);
        int p = rnd.next(2, maxP);
        int r = rnd.next(0, p - 1);
        for (int i = 0; i < n; i++) {
            int idx = i + 1;
            if (idx % p == r) extra[i] |= (1LL << b);
        }
    }

    a.assign(n, 0);
    for (int i = 0; i < n; i++) {
        long long v = commonMask | extra[i];

        int clearMax = hard ? 3 : 2;
        int kclear = rnd.next(0, clearMax);
        for (int t = 0; t < kclear && commonCnt > 0; t++) {
            int b = bits[rnd.next(0, commonCnt - 1)];
            v &= ~(1LL << b);
        }

        int addMax = hard ? 3 : 2;
        int kadd = rnd.next(0, addMax);
        for (int t = 0; t < kadd; t++) {
            int b = bits[rnd.next(0, 62)];
            v |= (1LL << b);
        }

        v &= FULL;
        if (v < 0) v = 0;
        a[i] = v;
    }

    auto pickDistinct = [&](int cnt) -> vector<int> {
        vector<int> chosen;
        vector<char> used(n, 0);
        while ((int)chosen.size() < cnt) {
            int x = rnd.next(0, n - 1);
            if (!used[x]) {
                used[x] = 1;
                chosen.push_back(x);
            }
        }
        return chosen;
    };

    vector<int> sp = pickDistinct(min(4, n));
    a[sp[0]] = FULL;
    if ((int)sp.size() >= 2) a[sp[1]] = 0;

    long long alt = 0;
    for (int b = 0; b <= 62; b++) if (b % 2 == 0) alt |= (1LL << b);
    alt &= FULL;
    if ((int)sp.size() >= 3) a[sp[2]] = alt;

    if ((int)sp.size() >= 4) {
        int b = rnd.next(0, 62);
        a[sp[3]] = (FULL ^ (1LL << b)) & FULL;
    }

    cout << n << "\n";
    for (int i = 0; i < n; i++) {
        if (i) cout << ' ';
        cout << a[i];
    }
    cout << "\n";
    return 0;
}