CF798 C. Mike and gcd problem
1 /* 2 CF798 C. Mike and gcd problem 3 http://codeforces.com/contest/798/problem/C 4 数论 贪心 5 题意:如果一个数列的gcd值大于1,则称之为美丽数列 6 给出数列a,可以将a_i 和 a_(i+1)换为其差和其和 7 如果可以变为美丽数列,输出YES并输出最少的变换次数 8 否则输出NO 9 思路: 10 如果变换a b 11 a b -> a-b a+b -> -2b 2a 12 因此变换两个可以把a b乘以2 13 而若a b都是奇数,只需变换一次 14 所以每次先找出相邻是奇数的情况ans++ 15 然后找相邻是奇偶的情况ans+=2 16 然而 17 比赛的时候居然把ans=gcd(ans,num[i]) 写成了ans=gcd(ans,i) 18 这居然还过了40组数据,也是醉了,雪崩! 19 */ 20 21 #include <cstdio> 22 #include <algorithm> 23 #include <cstring> 24 #include <cmath> 25 #include <vector> 26 #include <queue> 27 #include <iostream> 28 #include <map> 29 #include <set> 30 //#define test 31 using namespace std; 32 const int Nmax=1e6+7; 33 int n; 34 long long num[Nmax]; 35 long long gcd(long long a,long long b) 36 { 37 if(b==0) 38 return abs(a); 39 return gcd(b,a%b); 40 } 41 int main() 42 { 43 #ifdef test 44 #endif 45 scanf("%d",&n); 46 for(int i=1;i<=n;i++) 47 scanf("%I64d",&num[i]); 48 long long ans=0LL;//初始化一定要看仔细 49 for(int i=1;i<=n;i++) 50 { 51 ans=gcd(ans,num[i]);//num[i]一定不要写成i!!!!! 52 } 53 if(ans>1) 54 { 55 printf("YES\n0\n"); 56 return 0; 57 } 58 ans=0LL; 59 for(int i=1;i<n;i++) 60 { 61 if((num[i]&1) && (num[i+1]&1)) 62 { 63 ans++; 64 num[i]=2; 65 num[i+1]=2; 66 } 67 } 68 for(int i=1;i<=n;i++) 69 { 70 if(num[i]&1) 71 { 72 ans+=2; 73 } 74 } 75 printf("YES\n%I64d\n",ans); 76 return 0; 77 }