5
5 3
2 4
3 1
4 5
 4
2 4
3 2
2 1
 5
5 3
2 4
3 1
4 5
 2
1 2
 4
3 4
2 3
3 1
 10
8 10
2 9
7 8
4 1
7 3
4 7
2 5
2 4
4 6
 5
3 4
3 2
3 1
1 5
 3
1 2
2 3
 5
1 2
1 3
1 4
1 5

1 2
2 3
2 4
 1 3
2 4
3 5
4 5
 1 2
 1 3
2 3
3 4
 1 4
2 4
2 5
2 9
3 7
4 6
4 7
7 8
8 10
 1 3
1 5
2 3
3 4
 1 2
2 3
 1 2
1 3
1 4
1 5

#include <bits/stdc++.h>
using namespace std;
template <typename Arg1>
void __f(const char* name, Arg1&& arg1) {
  std::cerr << name << " : " << arg1 << endl;
}
template <typename Arg1, typename... Args>
void __f(const char* names, Arg1&& arg1, Args&&... args) {
  const char* comma = strchr(names + 1, ',');
  std::cerr.write(names, comma - names) << " : " << arg1 << " | ";
  __f(comma + 1, args...);
}
void ask(vector<bool>& vis, long long int c3) {
  cout << "? " << c3 << endl;
  return;
}
void solve() {
  long long int a = 1, b = 0, c = 0, t = 0, ans = 0, ans2 = 0, k = -1, c1 = 0,
                c2 = 0, c3 = 1, c4 = 0, n = 0, m = 0, x = 1e18;
  cin >> a;
  set<pair<long long int, long long int> > adj;
  vector<long long int> y;
  b = (a + 1) / 2;
  vector<bool> vis(a + 1);
  while (b--) {
    ask(vis, c3);
    c3 = 1, c4 = INT_MAX;
    for (int i = 0; i < a; ++i) {
      cin >> n;
      if (n < c4 and n and !vis[i + 1]) {
        c4 = n;
        c3 = i + 1;
      }
      if (n == 0) {
        c1 = i + 1;
        vis[i + 1] = true;
      } else if (n == 1) {
        y.push_back(i + 1);
        vis[i + 1] = true;
      }
    }
    for (auto i : y) adj.insert({max(c1, i), min(c1, i)});
    y.clear();
  }
  cout << "!" << endl;
  for (auto i : adj) {
    cout << i.first << " " << i.second << endl;
  }
}
int main() {
  ios_base::sync_with_stdio(false);
  cin.tie(NULL);
  cout.tie(NULL);
  clock_t z = clock();
  long long int qc = 1, additionalv;
  for (long long int i = 1; i <= qc; i++) {
    solve();
  }
  fprintf(stderr, "Real Time: % .4Lf\n",
          (long double)(clock() - z) / CLOCKS_PER_SEC),
      fflush(stderr);
}
