#include <bits/stdc++.h>
using namespace std;
const int inf = 1e9;
const long long Inf = 1e18;
const int N = 2e5 + 10;
const int mod = 0;
int gi() {
  int x = 0, o = 1;
  char ch = getchar();
  while ((ch < '0' || ch > '9') && ch != '-') ch = getchar();
  if (ch == '-') o = -1, ch = getchar();
  while (ch >= '0' && ch <= '9') x = x * 10 + ch - '0', ch = getchar();
  return x * o;
}
template <typename T>
bool chkmax(T &a, T b) {
  return a < b ? a = b, 1 : 0;
};
template <typename T>
bool chkmin(T &a, T b) {
  return a > b ? a = b, 1 : 0;
};
int add(int a, int b) { return a + b >= mod ? a + b - mod : a + b; }
int sub(int a, int b) { return a - b < 0 ? a - b + mod : a - b; }
void inc(int &a, int b) { a = (a + b >= mod ? a + b - mod : a + b); }
void dec(int &a, int b) { a = (a - b < 0 ? a - b + mod : a - b); }
int n, q, f[N], g[N], sum[N][26];
char s[N];
vector<int> fac[N];
struct suffix_array {
  int x[N], y[N], ws[N], wv[N], rnk[N], height[N], st[N][20], lg2[N], sa[N];
  int cmp(int *r, int a, int b, int l) {
    return r[a] == r[b] && r[a + l] == r[b + l];
  }
  void build(char *s) {
    memset(x, 0, sizeof(x)), memset(y, 0, sizeof(y)), memset(ws, 0, sizeof(ws)),
        memset(wv, 0, sizeof(wv)), memset(rnk, 0, sizeof(rnk)),
        memset(height, 0, sizeof(height)), memset(st, 0, sizeof(st)),
        memset(lg2, 0, sizeof(lg2)), memset(sa, 0, sizeof(sa));
    int m = 128, n = strlen(s + 1);
    for (int i = 0; i <= m; i++) ws[i] = 0;
    for (int i = 1; i <= n; i++) ws[x[i] = s[i]]++;
    for (int i = 1; i <= m; i++) ws[i] += ws[i - 1];
    for (int i = n; i; i--) sa[ws[x[i]]--] = i;
    for (int j = 1;; j <<= 1) {
      int p = 0;
      for (int i = n - j + 1; i <= n; i++) y[++p] = i;
      for (int i = 1; i <= n; i++)
        if (sa[i] > j) y[++p] = sa[i] - j;
      for (int i = 1; i <= n; i++) wv[i] = x[y[i]];
      for (int i = 0; i <= m; i++) ws[i] = 0;
      for (int i = 1; i <= n; i++) ws[wv[i]]++;
      for (int i = 1; i <= m; i++) ws[i] += ws[i - 1];
      for (int i = n; i; i--) sa[ws[wv[i]]--] = y[i];
      swap(x, y), x[sa[1]] = p = 1;
      for (int i = 2; i <= n; i++)
        x[sa[i]] = cmp(y, sa[i - 1], sa[i], j) ? p : ++p;
      if (p == n) break;
      m = p;
    }
    for (int i = 1; i <= n; i++) rnk[sa[i]] = i;
    for (int i = 1, j, k = 0; i <= n; height[rnk[i++]] = k)
      for (k ? k-- : 0, j = sa[rnk[i] - 1]; s[i + k] == s[j + k]; k++)
        ;
    for (int i = 1; i <= n; i++) st[i][0] = height[i];
    for (int j = 1; (1 << j) <= n; j++)
      for (int i = 1; i + (1 << j) - 1 <= n; i++)
        st[i][j] = min(st[i][j - 1], st[i + (1 << (j - 1))][j - 1]);
    for (int i = 2; i <= n; i++) lg2[i] = lg2[i >> 1] + 1;
  }
  int query(int l, int r) {
    int k = lg2[r - l + 1];
    return min(st[l][k], st[r - (1 << k) + 1][k]);
  }
  int lcp(int i, int j) {
    if (i == j) return n - i + 1;
    if (rnk[i] > rnk[j]) swap(i, j);
    return query(rnk[i] + 1, rnk[j]);
  }
  int queryminborder(int l, int r) {
    int rt = sqrt(n) + 1, ret = r - l + 1;
    for (int j = rnk[l]; j >= rnk[l] - rt && j; j--) {
      int i = sa[j], len = r - i + 1;
      if (l <= i && i <= r && lcp(l, i) >= len) chkmin(ret, len);
    }
    for (int j = rnk[l]; j <= rnk[l] + rt && j; j++) {
      int i = sa[j], len = r - i + 1;
      if (l <= i && i <= r && lcp(l, i) >= len) chkmin(ret, len);
    }
    return ret;
  }
} SA, rev_SA;
struct segment_tree {
  int tr[N << 2];
  segment_tree() { memset(tr, 0x3f, sizeof(tr)); }
  void init() { memset(tr, 0x3f, sizeof(tr)); }
  void modify(int o, int l, int r, int L, int R, int v) {
    if (L <= l && r <= R) {
      chkmin(tr[o], v);
      return;
    }
    int mid = (l + r) >> 1;
    if (L <= mid) modify((o << 1), l, mid, L, R, v);
    if (R > mid) modify((o << 1 | 1), mid + 1, r, L, R, v);
  }
  int query(int o, int l, int r, int p) {
    if (l == r) return tr[o];
    int mid = (l + r) >> 1;
    if (p <= mid)
      return min(tr[o], query((o << 1), l, mid, p));
    else
      return min(tr[o], query((o << 1 | 1), mid + 1, r, p));
  }
  void modify(int l, int r, int v) {
    if (l <= r) modify(1, 1, n, l, r, v);
  }
  int query(int p) { return query(1, 1, n, p); }
} sgt;
struct ST_table {
  int st[N][20], lg2[N];
  void build(int *a) {
    for (int i = 1; i <= n; i++) st[i][0] = a[i];
    for (int j = 1; (1 << j) <= n; j++)
      for (int i = 1; i + (1 << j) - 1 <= n; i++)
        st[i][j] = min(st[i][j - 1], st[i + (1 << (j - 1))][j - 1]);
    for (int i = 2; i <= n; i++) lg2[i] = lg2[i >> 1] + 1;
  }
  int query(int l, int r) {
    int k = lg2[r - l + 1];
    return min(st[l][k], st[r - (1 << k) + 1][k]);
  }
} ST_f;
int getminborder(int l, int r) {
  int len = r - l + 1, rt = sqrt(n) + 1;
  for (int i = 1; i <= len && i <= rt; i++)
    if (SA.lcp(l, r - i + 1) >= i) return i;
  return SA.queryminborder(l, r);
}
void getfac() {
  static int vis[N];
  memset(vis, 0, sizeof(vis));
  vis[1] = 1;
  for (int i = 2; i <= n; i++)
    if (!vis[i]) {
      fac[i].push_back(i);
      for (int j = i + i; j <= n; j += i) vis[j] = 1, fac[j].push_back(i);
    }
}
void getsum() {
  for (int i = 1; i <= n; i++) {
    for (int j = 0; j < 26; j++) sum[i][j] = sum[i - 1][j];
    ++sum[i][s[i] - 'a'];
  }
}
void solve(int *f) {
  sgt.init();
  for (int len = 1; len <= n / 2; len++)
    for (int i = 1; i + len <= n; i += len) {
      int x = i, y = i + len;
      int l = max(x - len + 1, x + 1 - rev_SA.lcp(n - x + 1, n - y + 1)),
          r = min(x, SA.lcp(x, y) - len + x);
      sgt.modify(l, r, 2 * len);
    }
  for (int i = 1; i <= n; i++) f[i] = sgt.query(i);
}
void getaa() {
  SA.build(s);
  reverse(s + 1, s + n + 1), rev_SA.build(s), solve(f);
  SA.build(s), reverse(s + 1, s + n + 1), rev_SA.build(s), solve(g);
  reverse(g + 1, g + n + 1);
  for (int i = 1; i <= n; i++) f[i] = i + f[i] - 1, g[i] = i - g[i] + 1;
}
void init() {
  getfac();
  getaa();
  getsum();
  SA.build(s);
  ST_f.build(f);
}
int have(int l, int r, char c) {
  return sum[r][c - 'a'] - sum[l - 1][c - 'a'] > 0;
}
int check_1(int l, int r) {
  if (r - l + 1 > 26) return 0;
  int vis[26];
  memset(vis, 0, sizeof(vis));
  for (int i = l; i <= r; i++) {
    if (vis[s[i] - 'a']) return 0;
    vis[s[i] - 'a'] = 1;
  }
  return 1;
}
int check1(int l, int r) {
  int len = r - l + 1;
  for (int x : fac[len]) {
    int y = len / x;
    if (SA.lcp(l, l + y) >= len - y) return 1;
  }
  return 0;
}
int check2(int l, int r) {
  if (f[l] <= r || g[r] >= l || getminborder(l, r) <= (r - l + 1) / 2) return 1;
  return 0;
}
int check3(int l, int r) {
  if (have(l + 1, r, s[l]) || have(l, r - 1, s[r]) || ST_f.query(l, r) <= r)
    return 1;
  return 0;
}
int query(int l, int r) {
  if (check_1(l, r)) return -1;
  if (check1(l, r)) return 1;
  if (check2(l, r)) return 2;
  if (check3(l, r)) return 3;
  return 4;
}
int main() {
  n = gi(), scanf("%s", s + 1), q = gi();
  init();
  while (q--) {
    int l = gi(), r = gi();
    printf("%d\n", query(l, r));
  }
  return 0;
}
