codeforces 676E 数学多项式
2016-05-26 21:22
344 查看
外国人写的太神看不懂,网上题解随机数这种乱搞都出来了,然后无奈自己推
该方法前面证明是对的然后会超long long所以不断改变mod水过,太菜真心想不到更好的方法。
证明:
一个多项式分解成 (x-k)和另一个多项式相乘
则
a
*x^n+a[n-1]*x^(n-1)+a[n-2]*x^(n-2)+a[n-3]*x^(n-3)+…+a[0]*x^0 =
(x-k) * (b[n-1]*x^(n-1)+b[n-2]*x^(n-2)+b[n-3]*x(n-3)+…..+b[0]*x^0)
则b[n-1]*x^n+(b[n-2]-k*b[n-1])*x^(n-1)+(b[n-3]-k*b[n-2])*x^(n-2)+…..+(b[0]-k*b[1])*x-k*b0*x^0;
所以
b[n-1] = a
;
b[n-2] = k*b[n-1] + a[n-1];
b[n-3] = k*b[n-2] + a[n-2];
……..
b[0] = k*b[1]+a[1];
-k*b[0] = a[0];
推导方法:前n个多项式就可以确定所有的解了。然后把b[0]带入最后一个方程式,如果矛盾就不行如果不矛盾就可以了。
这题就是线性代数,然而就我这线代渣渣水平推这个基本靠直觉。
然后这题的做法。如果k = 0要特殊讨论因为当k = 0时 b[0]*k必然为0;而别的b[i]无论是不是问号基本b[i] = a[i+1];所以a[0] = 0时 输出Yes不为0时输出No,a[0]为问号时看人能不能先手把它变0!
如果k!=0,就要解上面的方程了,
如果有问号的话那有用的式子小于等于n个,根据记忆中的线代定理可以确定一组可行解,但电脑后手的话可以让这个可行方程变得矛盾。。。
如果没有问号递推求方程按上面推导方法求出答案。
问题在于超long long 但只能想出这一种办法
该方法前面证明是对的然后会超long long所以不断改变mod水过,太菜真心想不到更好的方法。
证明:
一个多项式分解成 (x-k)和另一个多项式相乘
则
a
*x^n+a[n-1]*x^(n-1)+a[n-2]*x^(n-2)+a[n-3]*x^(n-3)+…+a[0]*x^0 =
(x-k) * (b[n-1]*x^(n-1)+b[n-2]*x^(n-2)+b[n-3]*x(n-3)+…..+b[0]*x^0)
则b[n-1]*x^n+(b[n-2]-k*b[n-1])*x^(n-1)+(b[n-3]-k*b[n-2])*x^(n-2)+…..+(b[0]-k*b[1])*x-k*b0*x^0;
所以
b[n-1] = a
;
b[n-2] = k*b[n-1] + a[n-1];
b[n-3] = k*b[n-2] + a[n-2];
……..
b[0] = k*b[1]+a[1];
-k*b[0] = a[0];
推导方法:前n个多项式就可以确定所有的解了。然后把b[0]带入最后一个方程式,如果矛盾就不行如果不矛盾就可以了。
这题就是线性代数,然而就我这线代渣渣水平推这个基本靠直觉。
然后这题的做法。如果k = 0要特殊讨论因为当k = 0时 b[0]*k必然为0;而别的b[i]无论是不是问号基本b[i] = a[i+1];所以a[0] = 0时 输出Yes不为0时输出No,a[0]为问号时看人能不能先手把它变0!
如果k!=0,就要解上面的方程了,
如果有问号的话那有用的式子小于等于n个,根据记忆中的线代定理可以确定一组可行解,但电脑后手的话可以让这个可行方程变得矛盾。。。
如果没有问号递推求方程按上面推导方法求出答案。
问题在于超long long 但只能想出这一种办法
#include<cstdio> #include<algorithm> #include<string> #include<iostream> using namespace std; #define LL long long #define mod 4000000017ll //乱搞 string a[110000]; LL n,k; LL ans[110000]; LL transform(string a) { LL l = a.size(),ans = 0,pre = 1; for(int i=l-1;i>=0;i--) { if(a[i]=='-')break; ans+=(a[i]-'0')*pre; pre*=10; } if(a[0]=='-')ans = -1*ans; return ans; } int main() { scanf("%I64d%I64d",&n,&k); int sum = 0; for(int i=0;i<=n;i++) { cin>>a[i]; if(a[i]=="?")sum++; ans[i] = transform(a[i]); } if(k==0)//k为0 { if(a[0]=="?"){ if((n+1-sum+1)%2)printf("No\n"); else printf("Yes\n"); } else { if(a[0]=="0")printf("Yes\n"); else printf("No\n"); } } else if(!sum)//无问号 { LL w = 0; for(int i=n;i>=1;i--) { w = k*w+ans[i]; w%=mod; } if(-1*w%mod*k%mod==ans[0]%mod)printf("Yes\n"); else printf("No\n"); } //有问号 else{ if((n+1)%2)printf("No\n"); else printf("Yes\n"); } return 0; }
相关文章推荐
- 练习打字第十四天!
- 三维坐标转换
- Ubuntu16.04安装openjdk-7-jdk
- 单例
- 抽象类实现多态
- 十年微博测试
- SmartImageView
- 先贤祠1
- LeetCode 31. Next Permutation
- Theano: CNMeM is disabled, CuDNN not available
- Javascript Lazyload图片延迟加载特效,降低HTPP连接次数,提高页面访问时间
- 海量数据处理常见面试题
- Hive 数据倾斜解决方案(调优)
- 《统计陷阱》读后感
- 嵌入式 Linux下编译并使用curl静态库
- maven创建项目命令
- 如何利用maven向本地仓库导入官网没有的jar包
- JDK 动态代理实现原理
- X64操作系统组件Jmail无法正常服务问题
- 学习进度12