标签:style blog http io ar color os sp for
题目链接:http://codeforces.com/problemset/problem/490/C
题目意思:给出一个可能有10^6 位长的字符串且没有前导0的整数,问能否一分为二,使得前面的一部分被 a 整除 且 后面那部分被 b 整除,可以的话输出 “YES” 和 划分后的两部分,否则输出“NO”.
看到字符串这么长,一下子就吓怕了~~~用 mod 即可!这些要靠数学积累吧......
好常规的方法做——暴力枚举,当然不能遗漏啦,所以从左至右直到倒数第二个数字,都要算出mod a 的结果且保存到 vis[] 数组里面(vis初始化为-1)。然后从右往前直到顺数第二个数字,算出 mod b 的结果,当这个结果为0(即可以被b整除),且vis[前一位数字] = 0(表示前面的数可以被a整除),还有一个容易遗漏的一点,就是没有前导0(对应代码中的 s[i] != ‘0‘)那么就代表找到一个解。遍历完之后都没有的话就表示没有答案,输出“NO”
1 #include <iostream> 2 #include <cstdio> 3 #include <cstdlib> 4 #include <cstring> 5 using namespace std; 6 7 const int maxn = 1e6 + 5; 8 int vis[maxn]; // 保存string中 0~len-1 个数字mod a 的结果 9 string s; 10 11 int main() 12 { 13 #ifndef ONLINE_JUDGE 14 freopen("in.txt", "r", stdin); 15 #endif // ONLINE_JUDGE 16 int a, b; 17 while (cin >> s >> a >> b) 18 { 19 memset(vis, -1, sizeof(vis)); 20 int tmp = 0; 21 int len = s.size(); 22 23 for (int i = 0; i < len-1; i++) // 至少要留一位给 b 嘛 24 { 25 tmp = (tmp * 10 + (s[i]-‘0‘)) % a; // 用到数学一些小知识 26 vis[i] = tmp; 27 } 28 29 int base = 1; 30 tmp = 0; 31 for (int i = len-1; i > 0; i--) // 同理,a都要至少留一位数 32 { 33 tmp = ((s[i]-‘0‘) * base + tmp) % b; 34 base = base * 10 % b; 35 if (tmp == 0 && !vis[i-1] && s[i] != ‘0‘) 36 { 37 cout << "YES" << endl; 38 cout << s.substr(0, i) << endl; 39 cout << s.substr(i, len-i) << endl; 40 return 0; 41 } 42 } 43 cout << "NO" << endl; 44 } 45 return 0; 46 }
codeforces 490C. Hacking Cypher 解题报告
标签:style blog http io ar color os sp for
原文地址:http://www.cnblogs.com/windysai/p/4130151.html