Advertisement
a53

origami

a53
Feb 25th, 2019
137
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 2.37 KB | None | 0 0
  1. #include <bits/stdc++.h>
  2.  
  3. #define Nmax 1005
  4. #define Mmax 1000005
  5. #define ll long long
  6.  
  7. using namespace std;
  8.  
  9. ifstream fin("origami.in");
  10. ofstream fout("origami.out");
  11.  
  12. int N, M;
  13. char *A[2][Mmax];
  14. char C[2 * Mmax];
  15. int L[Mmax], R[Mmax];
  16. int d[2 * Mmax];
  17. bitset <Mmax> pref, suf;
  18.  
  19. ll solve(int t, int N, int M)
  20. {
  21. for(int i = 1; i <= M; i++)
  22. L[i] = INT_MAX / 2, R[i] = INT_MAX / 2;
  23. for(int i = 1; i <= N; i++)
  24. {
  25. C[0] = '#';
  26. int le = 0, ri = 0, len = 0;
  27. for(int j = 1; j <= M; j++)
  28. C[2 * j - 1] = A[t][i][j], C[2 * j] = '#';
  29. int size = 2 * M;
  30. d[0] = 0;
  31. for(int j = 1; j <= size; j++)
  32. {
  33. if(j > ri)
  34. len = 0;
  35. else
  36. len = min(ri - j, d[le + ri - j]);
  37. while(j + len <= size && j - len >= 0 && C[j + len] == C[j - len])
  38. len++;
  39. len--;
  40. d[j] = len;
  41. if(j + len > ri)
  42. {
  43. ri = j + len;
  44. le = j - len;
  45. }
  46. }
  47. for(int j = 1; j <= M; j++)
  48. R[j] = min(R[j], d[2 * j] / 2);
  49. for(int j = 1; j <= M; j++)
  50. L[j] = R[j - 1];
  51. }
  52. pref.reset();
  53. suf.reset();
  54. suf[1] = true;
  55. int last = 1;
  56. for(int i = 2; i <= M; i++)
  57. if(L[i] > 0)
  58. {
  59. if(i - L[i] <= last)
  60. suf[i] = true, last = i;
  61. }
  62. pref[M] = true;
  63. last = M;
  64. for(int i = M; i >= 1; i--)
  65. if(R[i] > 0)
  66. {
  67. if(i + R[i] >= last)
  68. pref[i] = true, last = i;
  69. }
  70. ll ret = 0;
  71. int cnt = 0;
  72. for(int i = 1; i <= M; i++)
  73. {
  74. if(suf[i])
  75. cnt++;
  76. if(pref[i])
  77. ret += cnt;
  78. }
  79. return ret;
  80. }
  81.  
  82. int main()
  83. {
  84. fin >> N >> M;
  85. for(int i = 1; i <= N; i++)
  86. A[0][i] = new char[M + 5];
  87. for(int i = 1; i <= M; i++)
  88. A[1][i] = new char[N + 5];
  89. for(int i = 1; i <= N; i++)
  90. {
  91. fin >> (C + 1);
  92. A[0][i][0] = '#';
  93. for(int j = 1; j <= M; j++)
  94. A[0][i][j] = C[j];
  95. }
  96. for(int j = 1; j <= M; j++)
  97. {
  98. A[1][j][0] = '#';
  99. for(int i = 1; i <= N; i++)
  100. A[1][j][i] = A[0][i][j];
  101. }
  102. fout << solve(0, N, M) * solve(1, M, N) << "\n";
  103. return 0;
  104. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement