【Codeforces Round 354 (Div 2)E】【数学 多项式除法 讨论】The Last Fight Between Human and AI 多项式除以x-k是否值整除
来源:互联网 发布:c语言绚丽表白代码 编辑:程序博客网 时间:2024/05/01 06:40
100 years have passed since the last victory of the man versus computer in Go. Technologies made a huge step forward and robots conquered the Earth! It's time for the final fight between human and robot that will decide the faith of the planet.
The following game was chosen for the fights: initially there is a polynomial
Polynomial P(x) is said to be divisible by polynomial Q(x) if there exists a representation P(x) = B(x)Q(x), where B(x) is also some polynomial.
Some moves have been made already and now you wonder, is it true that human can guarantee the victory if he plays optimally?
The first line of the input contains two integers n and k (1 ≤ n ≤ 100 000, |k| ≤ 10 000) — the size of the polynomial and the integer k.
The i-th of the following n + 1 lines contain character '?' if the coefficient near xi - 1 is yet undefined or the integer value ai, if the coefficient is already known ( - 10 000 ≤ ai ≤ 10 000). Each of integers ai (and even an) may be equal to 0.
Please note, that it's not guaranteed that you are given the position of the game where it's computer's turn to move.
Print "Yes" (without quotes) if the human has winning strategy, or "No" (without quotes) otherwise.
1 2-1?
Yes
2 100-1000001
Yes
4 5?1?1?
No
In the first sample, computer set a0 to - 1 on the first move, so if human can set coefficient a1 to 0.5 and win.
In the second sample, all coefficients are already set and the resulting polynomial is divisible by x - 100, so the human has won.
#include<stdio.h>#include<iostream>#include<string.h>#include<string>#include<ctype.h>#include<math.h>#include<set>#include<map>#include<vector>#include<queue>#include<bitset>#include<algorithm>#include<time.h>using namespace std;void fre() { freopen("c://test//input.in", "r", stdin); freopen("c://test//output.out", "w", stdout); }#define MS(x,y) memset(x,y,sizeof(x))#define MC(x,y) memcpy(x,y,sizeof(x))#define MP(x,y) make_pair(x,y)#define ls o<<1#define rs o<<1|1typedef long long LL;typedef unsigned long long UL;typedef unsigned int UI;template <class T1, class T2>inline void gmax(T1 &a, T2 b) { if (b>a)a = b; }template <class T1, class T2>inline void gmin(T1 &a, T2 b) { if (b<a)a = b; }const int N = 1e5+10, M = 0, Z = 1e9 + 7, ms63 = 0x3f3f3f3f;int n, k;char s[12];int coe[N];bool check(int val){LL tmp = 0;int mod = abs(val - k);for (int i = n; i >= 0; --i){tmp = (tmp*val + coe[i]) % mod;}return tmp;}bool divide(){LL tmp = 0;for (int i = n; i >= 0; --i){tmp = k*tmp + coe[i];if (abs(tmp) >= 1e14)return 0;}return tmp == 0;}bool solve(){int qmark = 0;for (int i = 0; i <= n; ++i){scanf("%s", s);if (s[0] == '?')coe[i] = 1e9, ++qmark;else sscanf(s, "%d", &coe[i]);}if (k == 0){if (coe[0] == 0)return 1;if (coe[0] != 1e9)return 0;bool IplayFirst = (n + 1 - qmark & 1);return IplayFirst;}if (qmark){bool IplayLast = (n % 2 == 1);return IplayLast;}else{return divide();for (int tim = 1; tim <= 50; ++tim){if (check(rand()%10000*rand()))return 0;}return 1;}}int main(){while (~scanf("%d%d", &n, &k)){puts(solve() ? "Yes" : "No");}return 0;}/*【trick&&吐槽】样例1:1 2- 1 x ^ 00.5 x ^ 1- 1 + 0.5x = (x - 2)(0.5)样例2:2 100- 10000 x ^ 00 x ^ 11 x ^ 2- 10000 + x ^ 2 = (x - 100)(x + 100)【题意】给你一个多项式,最高项为n次,也就是说,该多项式可以写作:a[n] * x^n+a[n-1] * x^(n-1)+a[n-2] * x^(n-2)+a[n-3] * x^(n-3)+...a[0] * x^0然而系数a[]有的填了有的没填总体上的操作顺序是先robot再human,目前谁先手不确定。问你,是否有一个填充方案使得使得我们在把a[]填奥之后,满足这个多项式/(x-k),得到的结果依然是一个多项式(具体参考样例)n∈[1,1e6]k∈[-1e4,1e4]【类型】多项式除法问题随机数乱搞大法【分析】我们首先要学会观察。1,数据规模要求我们只有用O(n)级别的算法才能AC2,除以的式子是(x-k),我们发现该多项式,除了最低项a[0]以外,其它项都至少含有一个x。于是,一,如果k==0,这种情况下,我们只要使得a0不为0即可。1,a[0]已填,则填0必胜,填其它必败2,a[0]未填,则目前我们先手则必胜,否则必败二,如果k!=0,那么我们可以模拟一下多项式除法的过程,然后便可以发现——如果没填完,最后一手是谁谁必胜如果填完了,我们验证"该多项式/(x-k)"是否恒为0即可==================验证的方法可以是——1,随机算法(用check())函数实现如果"该多项式/(x-k)"恒为0,那么我们随机任何一个x,对于该多项式,最后求解都应当为0然而,如果只是取某一个或两个模数,是可能会被hack的,所以我们要多随机!2,除法模拟(用divide())函数实现a[n] * 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)a[n] * x^n =(x-k)* a[n]*x^(n-1) +k*a[n]*x^(n-1)于是我们可以模拟这个过程,通过判定:(1)不溢出,(2)最后为0来验证答案的正确性举例:2 100x^2-10000/(x-100)是否为0=100x-10000是否为0=0是否为0=YES【时间复杂度&&优化】O(kn)【数据】hack数据:针对1e9+7 && 1e9+94 1000063 0 160 0 10063x^3 + 160x + 100(x-10000)*/
- 【Codeforces Round 354 (Div 2)E】【数学 多项式除法 讨论】The Last Fight Between Human and AI 多项式除以x-k是否值整除
- Codeforces Round #354 (Div. 2) E - The Last Fight Between Human and AI
- [数学] codeforces 676E. The Last Fight Between Human and AI
- [Codeforces Round #354 DIV2E (CF676E)] The Last Fight Between Human and AI
- Codeforces 676E The Last Fight Between Human and AI (数论)
- codeforces 676E 数学多项式
- Codeforces Round #278 (Div. 2) 488C.Fight the Monster
- Codeforces Round #278 (Div. 2) C. Fight the Monster(暴力)
- Codeforces 711 E. ZS and The Birthday Paradox(数学)——Codeforces Round #369 (Div. 2)
- 【Codeforces Round 365 (Div 2)E】【乘除法DP map映射 约数分解】Mishka and Divisors n个数中选最小数量使得乘积为K的倍数
- Codeforces Round #281 (Div. 2) E. Vasya and Polynomial 数学 思考题
- Codeforces Round #280 (Div. 2) E. Vanya and Field (数学GCD)
- Codeforces Round #395 (Div. 2)E: Timofey and remoduling(数学+数论)
- ICM Technex 2017 and Codeforces Round #400 (Div. 1 + Div. 2, combined) E. The Holmes Children
- Codeforces Round #386 (Div. 2) C. Tram 数学、讨论
- Codeforces Round #181 (Div. 2) E. Empire Strikes Back N!∣∏K,i=1ai!
- Codeforces Round #435 (Div. 2) E. Mahmoud and Ehab and the function
- Codeforces Round #435 (Div. 2) E. Mahmoud and Ehab and the function
- java设计模式之策略模式
- 欢迎使用CSDN-markdown编辑器
- 架构设计:系统间通信(33)——其他消息中间件及场景应用(下3)
- 类会默认产生的成员函数
- 功能树Ztree的使用
- 【Codeforces Round 354 (Div 2)E】【数学 多项式除法 讨论】The Last Fight Between Human and AI 多项式除以x-k是否值整除
- hive启动移除 java.lang.RuntimeException: java.lang.IllegalArgumentException: java.net.URISyntaxException
- Android UI性能优化实战 识别绘制中的性能问题
- Frament与activity生命周期对比
- Velocity 是一个基于 Java 的模板引擎
- 矩阵乘法(Strassen算法/C++实现)
- 第十九章 斐波那契堆
- innerHTML和outerHTML有什么区别
- java7 fork-join