這題其實蠻水的?ios
題意就是說:c++
給定一個 1~n 的序列,每次挑兩個數 x y 合併,合併值爲 \(x+y+xy\) ,而後求不斷合併最後剩下的一個的最大值git
隨便搞搞發現答案應該是不管怎麼合併都同樣的,因此從左到右合併就行了,加上是第一題,大概就是這個結論ui
因而前綴信息處理一下每次直接輸出就行了...spa
//by Judge #include<bits/stdc++.h> #define Rg register #define fp(i,a,b) for(Rg int i=(a),I=(b)+1;i<I;++i) using namespace std; const int mod=1e9+7; const int M=1e6+3; typedef int arr[M]; #ifndef Judge #define getchar() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++) #endif char buf[1<<21],*p1=buf,*p2=buf; inline int read(){ int x=0,f=1; char c=getchar(); for(;!isdigit(c);c=getchar()) if(c=='-') f=-1; for(;isdigit(c);c=getchar()) x=x*10+c-'0'; return x*f; } char sr[1<<21],z[20];int CCF=-1,Z; inline void Ot(){fwrite(sr,1,CCF+1,stdout),CCF=-1;} inline void print(int x,char chr='\n'){ if(CCF>1<<20)Ot();if(x<0)sr[++CCF]=45,x=-x; while(z[++Z]=x%10+48,x/=10); while(sr[++CCF]=z[Z],--Z);sr[++CCF]=chr; } int n; arr q,f; inline int mul(Rg int x,Rg int y){return 1ll*x*y%mod;} inline int inc(Rg int x,Rg int y){return (x+=y)>=mod?x-mod:x;} int main(){ Rg int T=read(); fp(i,1,T) q[i]=read(); n=*max_element(q+1,q+1+T); fp(i,1,n) f[i]=inc(inc(f[i-1],i),mul(i,f[i-1])); fp(i,1,T) print(f[q[i]]); return Ot(),0; }
給出兩堆火柴,每次取某堆火柴的必定數,這個數字要能整除另外一堆火柴的個數,誰先取完某一堆的獲勝code
貌似是博弈論,看看這整除好像和 gcd 頗有關的樣子,因而發現先掌握主動權的人必勝(就是說輪到某人取的時候,某一堆火柴整除另外一堆火柴的個數大於 1 ,那麼這我的就能夠徹底控制局面了),而後加些特判就 ok 了,複雜度帶個 log 但常數真的小element
//by Judge #include<cstdio> #include<cstring> #include<iostream> #define Rg register #define fp(i,a,b) for(Rg int i=(a),I=(b)+1;i<I;++i) #define ll long long using namespace std; #ifndef Judge #define getchar() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++) #endif char buf[1<<21],*p1=buf,*p2=buf; inline ll read(){ ll x=0,f=1; char c=getchar(); for(;!isdigit(c);c=getchar()) if(c=='-') f=-1; for(;isdigit(c);c=getchar()) x=x*10+c-'0'; return x*f; } ll n,m,ans; #define swap(a,b) (a)^=(b)^=(a)^=(b) int main(){ fp(i,1,read()){ n=read(),m=read(); if(n<m) swap(n,m); ans=1; if(n%m==0){ puts("Ari"); goto end; } while(n<m<<1) n-=m,swap(n,m),ans^=1; puts(ans?"Ari":"Rich"); end:; } return 0; }
給出 n 個二維點,你能夠放置 n-1 條斜率爲 1 或 -1 的直線,而後要讓全部點裏最近的直線距離中的最大值最小,並輸出這個最小值乘上根號 2 的值,即求
\[ans=\sqrt2Min(~~~ MAX_{i=1}^n(dis _ i )~~~ )\]get
而後咱們發現只要求出全部的兩個點之間的 \({||x1-x2| -|y1-y2|| \over 2} + Min(|x1-x2|,|y1-y2|)\) 的最小值博客
然鵝 \(n^2\) 枚舉就完蛋了,因而咱們發現只須要通過每一個點記錄下該點的兩條斜率爲 -1 和 1 的直線,而後全部斜率相同的直線排個序,求兩條相鄰直線 \(y_1=(±1)x_1+b_1,y_2=(±1)x_2+b_2\) 中 \(|b_2-b_1|\)的最小差值就是答案了string
//by Judge #include<cstdio> #include<cstring> #include<iostream> #include<algorithm> #define Rg register #define fp(i,a,b) for(Rg int i=(a),I=(b)+1;i<I;++i) using namespace std; const int M=1e4+3; typedef int arr[M]; #ifndef Judge #define getchar() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++) #endif char buf[1<<21],*p1=buf,*p2=buf; inline bool cmin(int& a,int b){return a>b?a=b,1:0;} inline int read(){ int x=0,f=1; char c=getchar(); for(;!isdigit(c);c=getchar()) if(c=='-') f=-1; for(;isdigit(c);c=getchar()) x=x*10+c-'0'; return x*f; } int n,ans; arr x,y,a,b; int main(){ fp(i,1,read()){ n=read(),ans=1e9; fp(i,1,n) x[i]=read(),y[i]=read(),a[i]=y[i]-x[i],b[i]=x[i]+y[i]; sort(a+1,a+1+n),sort(b+1,b+1+n); fp(i,2,n) cmin(ans,a[i]-a[i-1]),cmin(ans,b[i]-b[i-1]); printf("%.8lf\n",ans/2.0); } return 0; }
關於其餘題目可能能夠看看博主博客園裏面有沒有寫