#include <bits/stdc++.h>
using namespace std;
const int inf = 0x3f3f3f3f;
long long sieve_size;
bitset<100010> bs;
vector<int> primes;
vector<int> pos, ind;
void sieve(long long upperbound) {
  sieve_size = upperbound + 1;
  bs.set();
  bs[0] = bs[1] = 0;
  for (long long i = 2; i <= sieve_size; i++)
    if (bs[i]) {
      for (long long j = i * i; j <= sieve_size; j += i) bs[j] = 0;
      primes.push_back(i);
    }
}
void doswap(int x, int y) {
  swap(pos[ind[x]], pos[ind[y]]);
  swap(ind[x], ind[y]);
}
int main() {
  sieve(100010);
  int n;
  scanf("%d", &n);
  vector<pair<int, int> > A(n);
  pos = vector<int>(n);
  ind = vector<int>(n);
  for (int i = (0); i < (n); ++i) {
    scanf("%d", &A[i].first);
    A[i].second = i;
    pos[A[i].second] = i;
    ind[i] = i;
  }
  sort((A).begin(), (A).end());
  vector<pair<int, int> > ops;
  for (int i = (0); i < (n); ++i) {
    int curr = pos[A[i].second];
    int goal = i;
    while (curr != goal) {
      int diff = abs(curr - goal) + 1;
      int ind =
          upper_bound((primes).begin(), (primes).end(), diff) - primes.begin();
      --ind;
      int next = curr - primes[ind] + 1;
      ops.push_back({next, curr});
      doswap(next, curr);
      curr = next;
    }
  }
  printf("%d\n", (int)ops.size());
  for (auto x : ops) {
    if (x.first > x.second) swap(x.first, x.second);
    printf("%d %d\n", x.first + 1, x.second + 1);
  }
  return 0;
}
