#pragma GCC optimize ("Ofast")
#include<bits/stdc++.h>
using namespace std;
void *wmem;
char memarr[96000000];
template<class T> inline void walloc1d(T **arr, int x, void **mem = &wmem){
  static int skip[16] = {0, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1};
  (*mem) = (void*)( ((char*)(*mem)) + skip[((unsigned long long)(*mem)) & 15] );
  (*arr)=(T*)(*mem);
  (*mem)=((*arr)+x);
}
struct mint{
  static unsigned md;
  static unsigned W;
  static unsigned R;
  static unsigned Rinv;
  static unsigned mdninv;
  static unsigned RR;
  unsigned val;
  mint(){
  }
  mint(int a){
    val = mulR(a);
  }
  mint(unsigned a){
    val = mulR(a);
  }
  mint(long long a){
    val = mulR(a);
  }
  mint(unsigned long long a){
    val = mulR(a);
  }
  int get_inv(long long a, int md){
    long long t=a;
    long long s=md;
    long long u=1;
    long long v=0;
    long long e;
    while(s){
      e=t/s;
      t-=e*s;
      u-=e*v;
      swap(t,s);
      swap(u,v);
    }
    if(u<0){
      u+=md;
    }
    return u;
  }
  void setmod(unsigned m){
    int i;
    unsigned t;
    W = 32;
    md = m;
    R = (1ULL << W) % md;
    RR = (unsigned long long)R*R % md;
    switch(m){
      case 104857601:
      Rinv = 2560000;
      mdninv = 104857599;
      break;
      case 998244353:
      Rinv = 232013824;
      mdninv = 998244351;
      break;
      case 1000000007:
      Rinv = 518424770;
      mdninv = 2226617417U;
      break;
      case 1000000009:
      Rinv = 171601999;
      mdninv = 737024967;
      break;
      case 1004535809:
      Rinv = 234947584;
      mdninv = 1004535807;
      break;
      case 1007681537:
      Rinv = 236421376;
      mdninv = 1007681535;
      break;
      case 1012924417:
      Rinv = 238887936;
      mdninv = 1012924415;
      break;
      case 1045430273:
      Rinv = 254466304;
      mdninv = 1045430271;
      break;
      case 1051721729:
      Rinv = 257538304;
      mdninv = 1051721727;
      break;
      default:
      Rinv = get_inv(R, md);
      mdninv = 0;
      t = 0;
      for(i=(0);i<((int)W);i++){
        if(t%2==0){
          t+=md;
          mdninv |= (1U<<i);
        }
        t /= 2;
      }
    }
  }
  unsigned mulR(unsigned a){
    return (unsigned long long)a*R%md;
  }
  unsigned mulR(int a){
    if(a < 0){
      a = a%((int)md)+(int)md;
    }
    return mulR((unsigned)a);
  }
  unsigned mulR(unsigned long long a){
    return mulR((unsigned)(a%md));
  }
  unsigned mulR(long long a){
    a %= md;
    if(a < 0){
      a += md;
    }
    return mulR((unsigned)a);
  }
  unsigned reduce(unsigned T){
    unsigned m = T * mdninv;
    unsigned t = (unsigned)((T + (unsigned long long)m*md) >> W);
    if(t >= md){
      t -= md;
    }
    return t;
  }
  unsigned reduce(unsigned long long T){
    unsigned m = (unsigned)T * mdninv;
    unsigned t = (unsigned)((T + (unsigned long long)m*md) >> W);
    if(t >= md){
      t -= md;
    }
    return t;
  }
  unsigned get(){
    return reduce(val);
  }
  mint &operator+=(mint a){
    val += a.val;
    if(val >= md){
      val -= md;
    }
    return *this;
  }
  mint &operator-=(mint a){
    if(val < a.val){
      val = val + md - a.val;
    }
    else{
      val -= a.val;
    }
    return *this;
  }
  mint &operator*=(mint a){
    val = reduce((unsigned long long)val*a.val);
    return *this;
  }
  mint &operator/=(mint a){
    return *this *= a.inverse();
  }
  mint operator+(mint a){
    return mint(*this)+=a;
  }
  mint operator-(mint a){
    return mint(*this)-=a;
  }
  mint operator*(mint a){
    return mint(*this)*=a;
  }
  mint operator/(mint a){
    return mint(*this)/=a;
  }
  mint operator+(int a){
    return mint(*this)+=mint(a);
  }
  mint operator-(int a){
    return mint(*this)-=mint(a);
  }
  mint operator*(int a){
    return mint(*this)*=mint(a);
  }
  mint operator/(int a){
    return mint(*this)/=mint(a);
  }
  mint operator+(long long a){
    return mint(*this)+=mint(a);
  }
  mint operator-(long long a){
    return mint(*this)-=mint(a);
  }
  mint operator*(long long a){
    return mint(*this)*=mint(a);
  }
  mint operator/(long long a){
    return mint(*this)/=mint(a);
  }
  mint operator-(void){
    mint res;
    if(val){
      res.val=md-val;
    }
    else{
      res.val=0;
    }
    return res;
  }
  operator bool(void){
    return val!=0;
  }
  operator int(void){
    return get();
  }
  operator long long(void){
    return get();
  }
  mint inverse(){
    int a = val;
    int b = md;
    int u = 1;
    int v = 0;
    int t;
    mint res;
    while(b){
      t = a / b;
      a -= t * b;
      swap(a, b);
      u -= t * v;
      swap(u, v);
    }
    if(u < 0){
      u += md;
    }
    res.val = (unsigned long long)u*RR % md;
    return res;
  }
  mint pw(unsigned long long b){
    mint a(*this);
    mint res;
    res.val = R;
    while(b){
      if(b&1){
        res *= a;
      }
      b >>= 1;
      a *= a;
    }
    return res;
  }
  bool operator==(int a){
    return mulR(a)==val;
  }
  bool operator!=(int a){
    return mulR(a)!=val;
  }
}
;
unsigned mint::md;
unsigned mint::W;
unsigned mint::R;
unsigned mint::Rinv;
unsigned mint::mdninv;
unsigned mint::RR;
mint operator+(int a, mint b){
  return mint(a)+=b;
}
mint operator-(int a, mint b){
  return mint(a)-=b;
}
mint operator*(int a, mint b){
  return mint(a)*=b;
}
mint operator/(int a, mint b){
  return mint(a)/=b;
}
mint operator+(long long a, mint b){
  return mint(a)+=b;
}
mint operator-(long long a, mint b){
  return mint(a)-=b;
}
mint operator*(long long a, mint b){
  return mint(a)*=b;
}
mint operator/(long long a, mint b){
  return mint(a)/=b;
}
inline void rd(int &x){
  int k;
  int m=0;
  x=0;
  for(;;){
    k = getchar_unlocked();
    if(k=='-'){
      m=1;
      break;
    }
    if('0'<=k&&k<='9'){
      x=k-'0';
      break;
    }
  }
  for(;;){
    k = getchar_unlocked();
    if(k<'0'||k>'9'){
      break;
    }
    x=x*10+k-'0';
  }
  if(m){
    x=-x;
  }
}
inline void rd(char &c){
  int i;
  for(;;){
    i = getchar_unlocked();
    if(i!=' '&&i!='\n'&&i!='\r'&&i!='\t'&&i!=EOF){
      break;
    }
  }
  c = i;
}
inline int rd(char c[]){
  int i;
  int sz = 0;
  for(;;){
    i = getchar_unlocked();
    if(i!=' '&&i!='\n'&&i!='\r'&&i!='\t'&&i!=EOF){
      break;
    }
  }
  c[sz++] = i;
  for(;;){
    i = getchar_unlocked();
    if(i==' '||i=='\n'||i=='\r'||i=='\t'||i==EOF){
      break;
    }
    c[sz++] = i;
  }
  c[sz]='\0';
  return sz;
}
inline void wt_L(char a){
  putchar_unlocked(a);
}
inline void wt_L(int x){
  int s=0;
  int m=0;
  char f[10];
  if(x<0){
    m=1;
    x=-x;
  }
  while(x){
    f[s++]=x%10;
    x/=10;
  }
  if(!s){
    f[s++]=0;
  }
  if(m){
    putchar_unlocked('-');
  }
  while(s--){
    putchar_unlocked(f[s]+'0');
  }
}
inline void wt_L(mint x){
  int i;
  i = (int)x;
  wt_L(i);
}
template<class T> int Factor_L(T N, T fac[], int fs[]){
  T i;
  int sz = 0;
  if(N%2==0){
    fac[sz] = 2;
    fs[sz] = 1;
    N /= 2;
    while(N%2==0){
      N /= 2;
      fs[sz]++;
    }
    sz++;
  }
  for(i=3;i*i<=N;i+=2){
    if(N%i==0){
      fac[sz] = i;
      fs[sz] = 1;
      N /= i;
      while(N%i==0){
        N /= i;
        fs[sz]++;
      }
      sz++;
    }
  }
  if(N > 1){
    fac[sz] = N;
    fs[sz] = 1;
    sz++;
  }
  return sz;
}
template<class T> int Divisor_L(T N, T res[], void *mem = wmem){
  int i;
  int j;
  int k;
  int s;
  int sz = 0;
  T *fc;
  int *fs;
  int fsz;
  walloc1d(&fc, 100, &mem);
  walloc1d(&fs, 100, &mem);
  fsz =Factor_L(N, fc, fs);
  res[sz++] = 1;
  for(i=(0);i<(fsz);i++){
    s = sz;
    k = s * fs[i];
    for(j=(0);j<(k);j++){
      res[sz++] = res[j] * fc[i];
    }
  }
  sort(res, res+sz);
  return sz;
}
template<class T, class S> inline T pow_L(T a, S b){
  T res = 1;
  res = 1;
  while(b){
    if(b&1){
      res *= a;
    }
    b >>= 1;
    a *= a;
  }
  return res;
}
inline double pow_L(double a, double b){
  return pow(a,b);
}
struct unionFind{
  int *d;
  int N;
  int M;
  inline void malloc(const int n){
    d = (int*)std::malloc(n*sizeof(int));
    M = n;
  }
  inline void free(void){
    std::free(d);
  }
  inline void walloc(const int n, void **mem=&wmem){
    walloc1d(&d, n, mem);
    M = n;
  }
  inline void init(const int n){
    int i;
    N = n;
    for(i=(0);i<(n);i++){
      d[i] = -1;
    }
  }
  inline void init(void){
    init(M);
  }
  inline int get(int a){
    int t = a;
    int k;
    while(d[t]>=0){
      t=d[t];
    }
    while(d[a]>=0){
      k=d[a];
      d[a]=t;
      a=k;
    }
    return a;
  }
  inline int connect(int a, int b){
    if(d[a]>=0){
      a=get(a);
    }
    if(d[b]>=0){
      b=get(b);
    }
    if(a==b){
      return 0;
    }
    if(d[a] < d[b]){
      d[a] += d[b];
      d[b] = a;
    }
    else{
      d[b] += d[a];
      d[a] = b;
    }
    return 1;
  }
  inline int operator()(int a){
    return get(a);
  }
  inline int operator()(int a, int b){
    return connect(a,b);
  }
  inline int& operator[](const int a){
    return d[a];
  }
  inline int size(int a){
    a = get(a);
    return -d[a];
  }
  inline int sizeList(int res[]){
    int i;
    int sz=0;
    for(i=(0);i<(N);i++){
      if(d[i]<0){
        res[sz++] = -d[i];
      }
    }
    return sz;
  }
}
;
#define MD 998244353
int N;
char X[200002];
int now[400002];
mint cntm[400002];
int vis[800002];
int gs;
vector<int> sm[400002];
vector<int> rv[400002];
int ys;
int y[100000];
mint solve(int dep, int st){
  int i;
  mint res;
  while(st < N && now[st] != -1){
    if(now[st] == X[st]){
      st++;
      continue;
    }
    if(now[st] > X[st]){
      return 0;
    }
    if(now[st] < X[st]){
      return (pow_L(mint(2),(gs-dep)));
    }
  }
  if(dep == gs){
    return 1;
  }
  res = 0;
  for(i=(0);i<(sm[dep].size());i++){
    now[sm[dep][i]] = 0;
  }
  for(i=(0);i<(rv[dep].size());i++){
    now[rv[dep][i]] = 1;
  }
  res += solve(dep+1, st);
  for(i=(0);i<(sm[dep].size());i++){
    now[sm[dep][i]] = 1;
  }
  for(i=(0);i<(rv[dep].size());i++){
    now[rv[dep][i]] = 0;
  }
  res += solve(dep+1, st);
  for(i=(0);i<(sm[dep].size());i++){
    now[sm[dep][i]] = -1;
  }
  for(i=(0);i<(rv[dep].size());i++){
    now[rv[dep][i]] = -1;
  }
  return res;
}
int main(){
  wmem = memarr;
  {
    mint x;
    x.setmod(MD);
  }
  int i;
  int j;
  int k;
  int km;
  unionFind uf;
  mint res;
  mint cnt;
  rd(N);
  rd(X);
  for(i=(0);i<(N);i++){
    X[i] -= '0';
  }
  res = 0;
  for(i=(0);i<(N);i++){
    res = res * 2 + X[i];
  }
  res += 1;
  res *= 2*N;
  uf.malloc(4*N);
  int Lj4PdHRW = N/3+1;
  for(i=(1);i<(Lj4PdHRW);i++){
    cntm[i] = 0;
    if(N % i == 0 && (N / i) % 2 == 1){
      uf.init(4*N);
      for(j=(0);j<(2*N-2*i);j++){
        uf(j, j+2*i);
        uf(2*N+j, 2*N+j+2*i);
      }
      for(j=(0);j<(N);j++){
        uf(j, 2*N+j+N);
        uf(j+2*N, j+N);
      }
      for(j=(0);j<(4*N);j++){
        vis[j] = -1;
      }
      gs = 0;
      for(j=(0);j<(N);j++){
        k = uf(j);
        if(k >= 2*N){
          km =k - 2*N;
        }
        else{
          km =k + 2*N;
        }
        if(vis[k] >= 0){
          sm[vis[k]].push_back(j);
          continue;
        }
        if(vis[km] >= 0){
          rv[vis[km]].push_back(j);
          continue;
        }
        vis[k] = gs++;
        sm[vis[k]].clear();
        rv[vis[k]].clear();
        sm[vis[k]].push_back(j);
      }
      for(j=(0);j<(N);j++){
        now[j] = -1;
      }
      cntm[i] = solve(0,0);
      ys =Divisor_L(i, y);
      for(j=(0);j<(ys-1);j++){
        cntm[i] -= cntm[y[j]];
      }
      cnt = cntm[i];
      res -= cnt * (2*N - 2*i);
    }
  }
  wt_L(res);
  wt_L('\n');
  return 0;
}
// cLay varsion 20190929-1

// --- original code ---
// #define MD 998244353
// int N;
// char X[200002];
// 
// int now[400002];
// mint cntm[400002];
// 
// int vis[800002];
// int gs;
// vector<int> sm[400002], rv[400002];
// 
// int ys, y[1d5];
// 
// mint solve(int dep, int st){
//   int i;
//   mint res;
// 
//   while(st < N && now[st] != -1){
//     if(now[st] == X[st]) st++, continue;
//     if(now[st] > X[st]) return 0;
//     if(now[st] < X[st]) return (mint(2) ** (gs-dep));
//   }
//   if(dep == gs) return 1;
// 
//   res = 0;
//   rep(i,sm[dep].size()) now[sm[dep][i]] = 0;
//   rep(i,rv[dep].size()) now[rv[dep][i]] = 1;
//   res += solve(dep+1, st);
//   rep(i,sm[dep].size()) now[sm[dep][i]] = 1;
//   rep(i,rv[dep].size()) now[rv[dep][i]] = 0;
//   res += solve(dep+1, st);
//   rep(i,sm[dep].size()) now[sm[dep][i]] = -1;
//   rep(i,rv[dep].size()) now[rv[dep][i]] = -1;
// 
//   return res;
// }
// 
// {
//   int i, j, k, km;
//   unionFind uf;
//   mint res, cnt;
//   rd(N,X);
//   rep(i,N) X[i] -= '0';
// 
//   res = 0;
//   rep(i,N) res = res * 2 + X[i];
//   res += 1;
//   res *= 2N;
// 
//   uf.malloc(4N);
// 
//   REP(i,1,N/3+1){
//     cntm[i] = 0;
//     if(N % i == 0 && (N / i) % 2 == 1){
//       uf.init(4N);
//       rep(j,2N-2i){
//         uf(j, j+2i);
//         uf(2N+j, 2N+j+2i);
//       }
//       rep(j,N){
//         uf(j, 2N+j+N);
//         uf(j+2N, j+N);
//       }
//       rep(j,4N) vis[j] = -1;
//       gs = 0;
//       rep(j,N){
//         k = uf(j);
//         km = if[k >= 2N, k - 2N, k + 2N];
//         if(vis[k] >= 0){
//           sm[vis[k]].push_back(j);
//           continue;
//         }
//         if(vis[km] >= 0){
//           rv[vis[km]].push_back(j);
//           continue;
//         }
//         vis[k] = gs++;
//         sm[vis[k]].clear();
//         rv[vis[k]].clear();
//         sm[vis[k]].push_back(j);
//       }
// 
// //    wt(gs);
// //    rep(j,gs){
// //      rep(k,sm[j].size()) printf(" +%d",sm[j][k]);
// //      rep(k,rv[j].size()) printf(" -%d",rv[j][k]);
// //      puts("");
// //    }
// 
//       rep(j,N) now[j] = -1;
//       cntm[i] = solve(0,0);
//       ys = Divisor(i, y);
//       rep(j,ys-1) cntm[i] -= cntm[y[j]];
// 
//       cnt = cntm[i];
// //      wt(i,cnt);
//       res -= cnt * (2N - 2i);
//     }
//   }
// 
//   wt(res);
// 
// 
// 
// 
// /*  {
//     int cnt = 0, r[100], tmp[100];
//   N = 18;
//   rep(mask,1<<N){
//     rep(i,N) tmp[i] = if[BIT_ith(mask,i), 1, 0];
//     rep(i,N) tmp[N+i] = 1 - tmp[i];
// 
//     rep(j,1,2N){
//       arrRot(j,2N,tmp,r);
//       rep(i,2N) if(r[i]!=tmp[i]) break;
//       if(i==2N) break;
//     }
//     if(j!=2N) wt(tmp(2N), ":", j), cnt++;
//   }
//     wt(cnt);
//   }*/
// }


Measured memory_bytes: 45940