#include <bits/stdc++.h>
using namespace std;
template <class T>
bool umin(T& a, const T& b) {
  return a > b ? a = b, true : false;
}
template <class T>
bool umax(T& a, const T& b) {
  return a < b ? a = b, true : false;
}
template <long long sz>
using tut = array<long long, sz>;
void usaco(string s) {
  freopen((s + ".in").c_str(), "r", stdin);
  freopen((s + ".out").c_str(), "w", stdout);
  ios::sync_with_stdio(0);
  cin.tie(0);
  cout.tie(0);
}
const long long N = 1e2 + 5;
const long long mod = 1e9 + 7;
const long long inf = 1e18;
const long double Pi = acos(-1);
long long n, m, k, t, q, ans, res, a[N];
vector<vector<string>> ask(long long l, long long r) {
  vector<vector<string>> second(n + 1);
  cout << "? " << l << " " << r << endl;
  for (long long i = l; i <= r; i++) {
    for (long long j = i; j <= r; j++) {
      string s;
      cin >> s;
      sort(s.begin(), s.end());
      second[(long long)s.size()].push_back(s);
    }
  }
  return second;
}
string find(long long n) {
  vector<vector<string>> all = ask(1, n);
  if (n == 1) {
    return all[n][0];
  }
  vector<vector<string>> second = ask(1, n - 1);
  map<string, long long> mm;
  for (auto x : all)
    for (auto s : x) mm[s]++;
  for (auto x : second)
    for (auto s : x) mm[s]--;
  vector<string> del, len(n + 1);
  for (auto x : mm)
    if (x.second == 0) del.push_back(x.first);
  for (auto x : del) mm.erase(x);
  for (auto x : mm) len[(long long)x.first.size()] = x.first;
  string s(n, '$');
  vector<long long> tot(26, 0);
  for (long long i = 1; i <= n; i++) {
    vector<long long> cur(26, 0);
    for (auto x : len[i]) cur[x - 'a']++;
    for (long long x = 0; x < 26; x++)
      if (cur[x] > tot[x]) s[i - 1] = x + 'a';
    swap(cur, tot);
  }
  reverse(s.begin(), s.end());
  return s;
}
void solve(long long t_case) {
  cin >> n;
  vector<vector<string>> all = ask(1, n);
  if (n == 1) {
    cout << "! " << all[n][0] << endl;
    return;
  }
  string half = find(n / 2);
  vector<vector<long long>> cnt(n + 1, vector<long long>(26, 0));
  for (long long i = 1; i <= n; i++) {
    for (auto x : all[i]) {
      for (long long j = 0; j < (long long)x.size(); j++) cnt[i][x[j] - 'a']++;
    }
  }
  string res(n, '$');
  for (long long i = 0; i < (long long)half.size(); i++) res[i] = half[i];
  for (long long i = n / 2; i >= 1; i--) {
    for (long long j = 0; j < 26; j++) {
      long long l = i + 1, r = n - i, cc = cnt[i + 1][j] - cnt[i][j], tcc = 0;
      for (long long i = l - 1; i < r; i++)
        if (res[i] - 'a' == j) tcc++;
      if (tcc < cc) {
        res[n - i - 1] = j + 'a';
        break;
      }
    }
  }
  vector<long long> cc(26, 0);
  for (auto x : all[n][0]) cc[x - 'a']++;
  for (auto x : res)
    if (isalpha(x)) cc[x - 'a']--;
  for (long long i = 0; i < 26; i++)
    if (cc[i]) res[n - 1] = i + 'a';
  cout << "! " << res << endl;
}
signed main() {
  ios::sync_with_stdio(0);
  cin.tie(0);
  cout.tie(0);
  if (0) {
    long long t;
    cin >> t;
    for (long long t_case = 1; t_case <= t; t_case++) solve(t_case);
  } else
    solve(1);
  return 0;
}
