【HDOJ】4333 Revolving Digits

扩展KMP基础题目。

  1 /* 4333 */
  2 #include <iostream>
  3 #include <sstream>
  4 #include <string>
  5 #include <map>
  6 #include <queue>
  7 #include <set>
  8 #include <stack>
  9 #include <vector>
 10 #include <deque>
 11 #include <algorithm>
 12 #include <cstdio>
 13 #include <cmath>
 14 #include <ctime>
 15 #include <cstring>
 16 #include <climits>
 17 #include <cctype>
 18 #include <cassert>
 19 #include <functional>
 20 #include <iterator>
 21 #include <iomanip>
 22 using namespace std;
 23 //#pragma comment(linker,"/STACK:102400000,1024000")
 24 
 25 #define sti                set<int>
 26 #define stpii            set<pair<int, int> >
 27 #define mpii            map<int,int>
 28 #define vi                vector<int>
 29 #define pii                pair<int,int>
 30 #define vpii            vector<pair<int,int> >
 31 #define rep(i, a, n)     for (int i=a;i<n;++i)
 32 #define per(i, a, n)     for (int i=n-1;i>=a;--i)
 33 #define clr                clear
 34 #define pb                 push_back
 35 #define mp                 make_pair
 36 #define fir                first
 37 #define sec                second
 38 #define all(x)             (x).begin(),(x).end()
 39 #define SZ(x)             ((int)(x).size())
 40 #define lson            l, mid, rt<<1
 41 #define rson            mid+1, r, rt<<1|1
 42 
 43 const int maxl = 1e5+5;
 44 char s[maxl], d[maxl*2];
 45 int nxt[maxl];
 46 int Next[maxl];
 47 int Ext[maxl*2];
 48 int slen, dlen;
 49 
 50 void getNxt(char *s, int len) {
 51     int i = 0, j = -1;
 52     
 53     nxt[0] = -1;
 54     while (i < len) {
 55         if (j==-1 || s[i]==s[j]) {
 56             ++i;
 57             ++j;
 58             nxt[i] = j;
 59         } else {
 60             j = nxt[j];
 61         }
 62     }
 63 }
 64 
 65 void getNext(char *s, int len) {
 66     int i = 0, j, k, p;
 67     int L;
 68     
 69     Next[0] = len;
 70     while (i<len-1 && s[i]==s[i+1])
 71         ++i;
 72     Next[1] = i;
 73     k = 1;
 74     
 75     for (i=2; i<len; ++i) {
 76         p = k + Next[k] - 1;
 77         L = Next[i - k];
 78         if (i+L <= p) {
 79             Next[i] = L;
 80         } else {
 81             j = p-i+1>0 ? p-i+1:0;
 82             while (i+j<len && s[i+j]==s[j])
 83                 ++j;
 84             Next[i] = j;
 85             k = i;
 86         }
 87     }
 88 }
 89 
 90 void getExtend(char *d, int dlen, char *s, int slen) {
 91     int i = 0, j, k, p;
 92     int L;
 93     int mnl = min(dlen, slen);
 94     
 95     while (i<mnl && d[i]==s[i])
 96         ++i;
 97     Ext[0] = i;
 98     k = 0;
 99     
100     for (i=1; i<dlen; ++i) {
101         p = k + Ext[k] - 1;
102         L = Next[i - k];
103         if (i+L <= p) {
104             Ext[i] = L;
105         } else {
106             j = (p-i+1)>0 ? p-i+1:0;
107             while (i+j<dlen && j<slen && d[i+j]==s[j])
108                 ++j;
109             Ext[i] = j;
110             k = i;
111         }
112     }
113 }
114 
115 void solve() {    
116     strcpy(d, s);
117     strcat(d, s);
118     slen = strlen(s);
119     dlen = slen << 1;
120     
121     getNext(s, slen);
122     getExtend(d, dlen, s, slen);
123     getNxt(s, slen);
124     
125     int mod = slen - nxt[slen];
126     int tmp = 1;
127     if (slen%mod == 0)
128         tmp = slen / mod;
129     
130     int ln, en, gn;
131     
132     ln = gn = en = 0;
133     rep(i, 0, slen) {
134         if (Ext[i] >= slen)
135             ++en;
136         else if (d[i+Ext[i]] < s[Ext[i]])
137             ++ln;
138         else
139             ++gn;
140     }
141     
142     ln /= tmp;
143     en /= tmp;
144     gn /= tmp;
145     printf("%d %d %d\n", ln, en, gn);
146 }
147 
148 int main() {
149     ios::sync_with_stdio(false);
150     #ifndef ONLINE_JUDGE
151         freopen("data.in", "r", stdin);
152         freopen("data.out", "w", stdout);
153     #endif
154     
155     int t;
156     
157     scanf("%d", &t);
158     rep(tt, 1, t+1) {
159         scanf("%s", s);
160         printf("Case %d: ", tt);
161         solve();
162     }
163     
164     #ifndef ONLINE_JUDGE
165         printf("time = %d.\n", (int)clock());
166     #endif
167     
168     return 0;
169 }

 

你可能感兴趣的:(【HDOJ】4333 Revolving Digits)