NOIP2014 解题报告·水渣记
2014-11-08 17:45
288 查看
Day 1:
第一次参加noip。小激动,小紧张,这些正常的情绪就不用说了。唯一值得一提的是 我早上步行去郑大工学院的时候迷路了,直接转进了隔壁的河南农大,绕了半天找不到机房,还给几个同学打了电话可就是没人接……于是就在保安异样的目光下灰溜溜地走出了校门= =...然后还算好,总算提前半个小时来到了考点。。。
然后找座位的时候我遇到了奇怪的事情!!我的座位旁边是夏五岳……同校+同语言……天知道负责人的随机数生成器是出了什么问题= =不过看起来我们似乎没有被监考的志愿者盯上?那就这样吧= =于是,按照平时的习惯,我先敲好了头文件和快速读入……(别问我为什么还有快速读入……我只是懒得每次打scanf又怕cin被卡……)然后……看题……
A: 生活大爆炸版石头剪刀布
给出五种手势的胜负关系,A、B的出拳循环节和总共进行的轮数N,求游戏结束时两人各自的输赢次数。
N <= 200。N <= 200。N <= 200。N <= 200。
QAQ……请告诉我我没有看错数据范围。请告诉我200遍我没有看错数据范围。不对……我是不是走错考场考成普及组了?可是普及组不应该是下午比赛吗……好吧好吧,我再检查200遍题目就开始敲代码。。。
于是开考后三十分钟,我开始了无脑模拟。话说这题要是数据范围再大那么几个零是不是就可以变成数论题了?= = 看来出题人有着特别的送分技巧……就这么敲完了模拟。果断开下一题?算了还是再检查200遍题目吧……万一理解错了呢……
1 /*======================================================*/
2 /*========================ASM.DEF=======================*/
3 /*======================================================*/
4 #include <cstdio>
5 #include <cctype>
6 #include <iostream>
7 #include <cmath>
8 #include <cstring>
9 #include <algorithm>
10 #include <vector>
11 #include <queue>
12 #include <deque>
13 #include <ctime>
14 using namespace std;
15 #if defined WJX_Asm_Def_DEBUG
16 FILE *in = fopen("test", "r");
17 #define out stdout
18 #else
19 FILE *in = fopen("equationa.in", "r");
20 FILE *out = fopen("equationa.out", "w");
21 #endif
22 inline bool getd(int &x){
23 int c = fgetc(in);
24 bool minus = 0;
25 while(c != '-' && c != EOF && !isdigit(c))c = fgetc(in);
26 if(c == EOF)return 0;
27 if(c == '-'){
28 x = 0;
29 minus = 1;
30 }
31 else x = c - '0';
32 while(isdigit(c = fgetc(in)))x = x * 10 - '0' + c;
33 return 1;
34 }
35 #define iter(v) v::iterator
36 #define pb push_back
37 #define pf push_front
38 #define ppf pop_front
39 /*===========================================================*/
40 const int maxn = 100 + 3, maxm = 1000000 + 10, maxl = 10000 + 10;
41 int n, m, len[maxm] = {0}, a[maxn][maxl], amod[maxn] = {0};
42 bool neg[maxn] = {0};
43 int P[maxm], Pcnt = 0, basep;
44 bool not_ans[maxl] = {0};
45
46 inline void euler(){
47 bool not_p[maxl] = {0};
48 int i, j;
49 for(i = 2;i < maxl;++i){
50 if(!not_p[i])P[Pcnt++] = i;
51 for(j = 0;j < Pcnt;++j){
52 if(i * P[j] > maxl)break;
53 not_p[i * P[j]] = 1;
54 if(i % P[j] == 0)break;
55 }
56 }
57 }
58
59 inline void init(){
60 srand(time(NULL));
61 euler();
62 getd(n), getd(m);
63 int i, c;
64 for(i = 0;i <= n;++i){
65 c = fgetc(in);
66 while(!isdigit(c) && c != '-')c = fgetc(in);
67 if(c == '-'){
68 neg[i] = 1;
69 c = fgetc(in);
70 }
71 a[i][len[i]++] = c - '0';
72 while(isdigit(c = fgetc(in)))
73 a[i][len[i]++] = c - '0';
74 }
75 }
76
77 inline bool getamod(int p){
78 int i, j;
79 bool ans = 0;
80 for(i = 0;i <= n;++i){
81 amod[i] = a[i][0] % p;
82 for(j = 1;j < len[i];++j)
83 amod[i] = (amod[i] * 10 + a[i][j]) % p;
84 if(amod[i])ans = 1;
85 }
86 return ans;
87 }
88
89 inline int f(int x, int p){
90 int i, k = 1, ans = 0, t;
91 x %= p;
92 for(i = 0;i <= n;++i){
93 t = neg[i] ? p - amod[i] : amod[i];
94 ans = (ans + k * t) % p;
95 k = (k * x) % p;
96 }
97 return ans;
98 }
99
inline void work(){
int i, k, p, cnt = m;
bool not_A[maxm] = {0};
i = lower_bound(P, P + Pcnt, (int)sqrt((double)m * n)) - P;
basep = P[i];
while(!getamod(basep))basep = P[--i];
for(i = 0;i < basep;++i)
if(f(i, basep))not_ans[i] = 1;
k = 5;
while(k || cnt > n){
--k;
p = P[rand() % Pcnt];
while(!getamod(p))p = P[rand() % Pcnt];
for(i = 1;i <= m;++i){
if(not_A[i])continue;
if(not_ans[i % basep]){
not_A[i] = 1;
--cnt;
continue;
}
if(f(i, p))not_A[i] = 1, --cnt;
}
}
fprintf(out, "%d\n", cnt);
for(i = 1;i <= m;++i)
if(!not_A[i])
fprintf(out, "%d\n", i);
}
int main(){
init();
work();
return 0;
}
分段,用hash判断
第一次参加noip。小激动,小紧张,这些正常的情绪就不用说了。唯一值得一提的是 我早上步行去郑大工学院的时候迷路了,直接转进了隔壁的河南农大,绕了半天找不到机房,还给几个同学打了电话可就是没人接……于是就在保安异样的目光下灰溜溜地走出了校门= =...然后还算好,总算提前半个小时来到了考点。。。
然后找座位的时候我遇到了奇怪的事情!!我的座位旁边是夏五岳……同校+同语言……天知道负责人的随机数生成器是出了什么问题= =不过看起来我们似乎没有被监考的志愿者盯上?那就这样吧= =于是,按照平时的习惯,我先敲好了头文件和快速读入……(别问我为什么还有快速读入……我只是懒得每次打scanf又怕cin被卡……)然后……看题……
A: 生活大爆炸版石头剪刀布
给出五种手势的胜负关系,A、B的出拳循环节和总共进行的轮数N,求游戏结束时两人各自的输赢次数。
N <= 200。N <= 200。N <= 200。N <= 200。
QAQ……请告诉我我没有看错数据范围。请告诉我200遍我没有看错数据范围。不对……我是不是走错考场考成普及组了?可是普及组不应该是下午比赛吗……好吧好吧,我再检查200遍题目就开始敲代码。。。
于是开考后三十分钟,我开始了无脑模拟。话说这题要是数据范围再大那么几个零是不是就可以变成数论题了?= = 看来出题人有着特别的送分技巧……就这么敲完了模拟。果断开下一题?算了还是再检查200遍题目吧……万一理解错了呢……
1 /*======================================================*/
2 /*========================ASM.DEF=======================*/
3 /*======================================================*/
4 #include <cstdio>
5 #include <cctype>
6 #include <iostream>
7 #include <cmath>
8 #include <cstring>
9 #include <algorithm>
10 #include <vector>
11 #include <queue>
12 #include <deque>
13 #include <ctime>
14 using namespace std;
15 #if defined WJX_Asm_Def_DEBUG
16 FILE *in = fopen("test", "r");
17 #define out stdout
18 #else
19 FILE *in = fopen("equationa.in", "r");
20 FILE *out = fopen("equationa.out", "w");
21 #endif
22 inline bool getd(int &x){
23 int c = fgetc(in);
24 bool minus = 0;
25 while(c != '-' && c != EOF && !isdigit(c))c = fgetc(in);
26 if(c == EOF)return 0;
27 if(c == '-'){
28 x = 0;
29 minus = 1;
30 }
31 else x = c - '0';
32 while(isdigit(c = fgetc(in)))x = x * 10 - '0' + c;
33 return 1;
34 }
35 #define iter(v) v::iterator
36 #define pb push_back
37 #define pf push_front
38 #define ppf pop_front
39 /*===========================================================*/
40 const int maxn = 100 + 3, maxm = 1000000 + 10, maxl = 10000 + 10;
41 int n, m, len[maxm] = {0}, a[maxn][maxl], amod[maxn] = {0};
42 bool neg[maxn] = {0};
43 int P[maxm], Pcnt = 0, basep;
44 bool not_ans[maxl] = {0};
45
46 inline void euler(){
47 bool not_p[maxl] = {0};
48 int i, j;
49 for(i = 2;i < maxl;++i){
50 if(!not_p[i])P[Pcnt++] = i;
51 for(j = 0;j < Pcnt;++j){
52 if(i * P[j] > maxl)break;
53 not_p[i * P[j]] = 1;
54 if(i % P[j] == 0)break;
55 }
56 }
57 }
58
59 inline void init(){
60 srand(time(NULL));
61 euler();
62 getd(n), getd(m);
63 int i, c;
64 for(i = 0;i <= n;++i){
65 c = fgetc(in);
66 while(!isdigit(c) && c != '-')c = fgetc(in);
67 if(c == '-'){
68 neg[i] = 1;
69 c = fgetc(in);
70 }
71 a[i][len[i]++] = c - '0';
72 while(isdigit(c = fgetc(in)))
73 a[i][len[i]++] = c - '0';
74 }
75 }
76
77 inline bool getamod(int p){
78 int i, j;
79 bool ans = 0;
80 for(i = 0;i <= n;++i){
81 amod[i] = a[i][0] % p;
82 for(j = 1;j < len[i];++j)
83 amod[i] = (amod[i] * 10 + a[i][j]) % p;
84 if(amod[i])ans = 1;
85 }
86 return ans;
87 }
88
89 inline int f(int x, int p){
90 int i, k = 1, ans = 0, t;
91 x %= p;
92 for(i = 0;i <= n;++i){
93 t = neg[i] ? p - amod[i] : amod[i];
94 ans = (ans + k * t) % p;
95 k = (k * x) % p;
96 }
97 return ans;
98 }
99
inline void work(){
int i, k, p, cnt = m;
bool not_A[maxm] = {0};
i = lower_bound(P, P + Pcnt, (int)sqrt((double)m * n)) - P;
basep = P[i];
while(!getamod(basep))basep = P[--i];
for(i = 0;i < basep;++i)
if(f(i, basep))not_ans[i] = 1;
k = 5;
while(k || cnt > n){
--k;
p = P[rand() % Pcnt];
while(!getamod(p))p = P[rand() % Pcnt];
for(i = 1;i <= m;++i){
if(not_A[i])continue;
if(not_ans[i % basep]){
not_A[i] = 1;
--cnt;
continue;
}
if(f(i, p))not_A[i] = 1, --cnt;
}
}
fprintf(out, "%d\n", cnt);
for(i = 1;i <= m;++i)
if(!not_A[i])
fprintf(out, "%d\n", i);
}
int main(){
init();
work();
return 0;
}
分段,用hash判断
相关文章推荐
- NOIP2014 飞扬的小鸟 解题报告(DP)
- NOIP2014提高组复赛解题报告
- NOIP2014普及组复赛子矩阵解题报告
- [解题报告] NOIP 2014 提高组Day2试题
- NOIP2014 无线网络发射器选址 解题报告(水题)
- 2016.7.15 NOIP2014模拟试题解题报告(又名:方克顺和他的正余弦朋友们(
- LuoguP1941[NOIP2014] 飞扬的小鸟 解题报告【背包型DP】
- NOIP2014普及组解题报告 ----王煜伟
- NOIP2014提高组D.发射器选址(解题报告)
- 2016.7.18 NOIP2014提高组day1解题报告
- NOIP2014 提高组复赛解题报告
- NOIP2014 寻找道路 解题报告(dfs+bfs)
- 2016.9.3测试解题报告(NOIP2014 day1 day2)
- NOIP2014解方程解题报告
- [NOIP2014]子矩阵解题报告
- codevs 3732 NOIP2014 解方程 解题报告
- 【NOIP2014提高组】【Day1】【解题报告】
- [解题报告] NOIP 2014 提高组Day1试题
- NOIP2014 解方程 解题报告(取模运算+秦九韶定理)
- Noip 2014 提高组复赛 解题报告