Problem p00889 (C++) — buggy submission, verdict: Memory Limit Exceeded

#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <map>
#include <queue>
#include <vector>
inline int Input() {
  int ret = 0;
  bool isN = 0;
  char c = getchar();
  while (c < '0' || c > '9') {
    if (c == '-')
      isN = 1;
    c = getchar();
  }
  while (c >= '0' && c <= '9') {
    ret = ret * 10 + c - '0';
    c = getchar();
  }
  return isN ? -ret : ret;
}

inline void Output(long long x) {
  if (x < 0) {
    putchar('-');
    x = -x;
  }
  int len = 0, data[20];
  while (x) {
    data[len++] = x % 10;
    x /= 10;
  }
  if (!len)
    data[len++] = 0;
  while (len--)
    putchar(data[len] + 48);
  putchar('\\n');
}
#pragma comment(linker, "/STACK:124000000,124000000")
#include <map>
#include <queue>
#include <vector>
#define eps 1e-10
#define INF 2000000009
#define maxn 150050
#define maxm 2500010
#define mod 1000000
#define llINF 1LL << 60
using namespace std;

int a[100005];
int sum[100005];
map<int, int> mp;
int main() {
  int n, s, w, q;
  while (scanf("%d%d%d%d", &n, &s, &w, &q) && n) {
    mp.clear();
    memset(sum, 0, sizeof(sum));
    for (int i = 0; i < n; i++) {
      a[i] = (s / 7) % 10;
      if (s & 1) {
        s = (s / 2) ^ w;
      } else {
        s = s / 2;
      }
    }
    //        for(int i=0;i<n;i++)
    //            printf("%d",a[i]);
    //        printf("\\n");
    int i = 0;
    int ans = 0;
    while (a[i] == 0 && i < n)
      i++;
    if (q == 2 || q == 5) {
      int t = i;
      for (i; i < n; i++) {
        if (a[i] % q == 0) {
          ans += i + 1 - t;
          if (a[i] == 0)
            ans--;
        }
        if (a[i] == 0)
          t++;
      }
    } else {
      int cnt = 2;
      int t = i;
      int ttt = 0;
      int ten = 1;
      mp[0] = 1;
      sum[1] = 1;
      for (i = n - 1; i >= t; i--) {
        ttt = (a[i] * ten % q + ttt) % q;
        ten = ten * 10 % q;
        if (a[i] == 0) {
          ans -= sum[mp[ttt]];
        }
        if (mp[ttt] == 0) {
          mp[ttt] = cnt++;
          sum[cnt - 1] = 1;
        } else {
          sum[mp[ttt]]++;
        }
      }
      for (int i = 0; i < cnt; i++) {
        long long tmp = sum[i];
        // printf("%d %I64d\\n",i,tmp);
        tmp = tmp * (tmp - 1) / 2;
        ans += tmp;
      }
    }
    printf("%d\\n", ans);
  }
  return 0;
}

Error: MLE

Fixed submission:

#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <map>
#include <queue>
#include <vector>
inline int Input() {
  int ret = 0;
  bool isN = 0;
  char c = getchar();
  while (c < '0' || c > '9') {
    if (c == '-')
      isN = 1;
    c = getchar();
  }
  while (c >= '0' && c <= '9') {
    ret = ret * 10 + c - '0';
    c = getchar();
  }
  return isN ? -ret : ret;
}

inline void Output(long long x) {
  if (x < 0) {
    putchar('-');
    x = -x;
  }
  int len = 0, data[20];
  while (x) {
    data[len++] = x % 10;
    x /= 10;
  }
  if (!len)
    data[len++] = 0;
  while (len--)
    putchar(data[len] + 48);
  putchar('\\n');
}
#pragma comment(linker, "/STACK:124000000,124000000")
#include <map>
#include <queue>
#include <vector>
#define eps 1e-10
#define INF 2000000009
#define maxn 150050
#define maxm 2500010
#define mod 1000000
#define llINF 1LL << 60
using namespace std;

int a[100005];
int sum[100005];
map<int, int> mp;
int main() {
  int n, s, w, q;
  while (scanf("%d%d%d%d", &n, &s, &w, &q) && n) {
    mp.clear();
    for (int i = 0; i < n; i++) {
      a[i] = (s / 7) % 10;
      if (s & 1) {
        s = (s / 2) ^ w;
      } else {
        s = s / 2;
      }
    }
    //        for(int i=0;i<n;i++)
    //            printf("%d",a[i]);
    //        printf("\\n");
    int i = 0;
    int ans = 0;
    while (a[i] == 0 && i < n)
      i++;
    if (q == 2 || q == 5) {
      int t = i;
      for (i; i < n; i++) {
        if (a[i] % q == 0) {
          ans += i + 1 - t;
          if (a[i] == 0)
            ans--;
        }
        if (a[i] == 0)
          t++;
      }
    } else {
      int t = i;
      sum[n] = 0;
      int ten = 1;
      int cnt = 0;
      mp[0] = 1;
      for (i = n - 1; i >= t; i--) {
        sum[i] = (a[i] * ten % q + sum[i + 1]) % q;
        ten = ten * 10 % q;
        if (a[i] == 0) {
          ans -= mp[sum[i]];
        }
        mp[sum[i]]++;
      }
      for (int i = 0; i < q; i++) {
        long long tmp = mp[i];
        // printf("%d %I64d\\n",i,tmp);
        tmp = tmp * (tmp - 1) / 2;
        ans += tmp;
      }
    }
    printf("%d\\n", ans);
  }
  return 0;
}