連續不知道多少場了,都是一場10名以內一場20以外。。。波動極大。。。還極有規律。。。
拿到這套題,看到T1大模擬無話可說。
然后考場上我覺得T2很簡單。。。。然后就碼了兩個半小時。
T3數據水了暴力70。。。
T1:磚塊
大模擬。其實也不大。。。
記錄上下左右前后邊界然后滾就是了
閑得慌打hash_map

1 #include<cstdio> 2 #include<iostream> 3 using namespace std; 4 #define P(a,b) make_pair(a,b) 5 struct hash_map{ 6 int fir[100003],l[100005],tox[100005],toy[100005],v[100005],cnt; 7 #define mod 100003 8 int& operator[](pair<int,int>p){ 9 int x=p.first,y=p.second,hsh=(x*y%mod+mod)%mod; 10 for(int i=fir[hsh];i;i=l[i])if(tox[i]==x&&toy[i]==y)return v[i]; 11 l[++cnt]=fir[hsh];fir[hsh]=cnt;tox[cnt]=x;toy[cnt]=y;v[cnt]=0;return v[cnt]; 12 } 13 void clear(){for(int i=0;i<mod;++i)fir[i]=0;cnt=0;} 14 }m; 15 int mxt,u,l,r,f,b;char s[105]; 16 void n_turn(){ 17 int U=u,L=l,R=r,F=f,B=b; 18 u=B-F;f=B;b=B+U; 19 for(int i=l;i<r;++i)for(int j=f;j<b;++j){int &x=m[P(i,j)];x++,mxt=max(mxt,x);} 20 } 21 void s_turn(){ 22 int U=u,L=l,R=r,F=f,B=b; 23 u=B-F;b=F;f=F-U; 24 for(int i=l;i<r;++i)for(int j=f;j<b;++j){int &x=m[P(i,j)];x++,mxt=max(mxt,x);} 25 } 26 void w_turn(){ 27 int U=u,L=l,R=r,F=f,B=b; 28 u=R-L;r=L;l=L-U; 29 for(int i=l;i<r;++i)for(int j=f;j<b;++j){int &x=m[P(i,j)];x++,mxt=max(mxt,x);} 30 } 31 void e_turn(){ 32 int U=u,L=l,R=r,F=f,B=b; 33 u=R-L;l=R;r=R+U; 34 for(int i=l;i<r;++i)for(int j=f;j<b;++j){int &x=m[P(i,j)];x++,mxt=max(mxt,x);} 35 } 36 int main(){//freopen("ex_block2.in","r",stdin); 37 int t;scanf("%d",&t); 38 while(t--){ 39 l=0,r=1,f=0,b=1,mxt=0;scanf("%d%s",&u,s);m.clear();m[P(0,0)]++; 40 for(int i=0;s[i];++i) 41 if(s[i]=='N')n_turn(); 42 else if(s[i]=='E')e_turn(); 43 else if(s[i]=='W')w_turn(); 44 else if(s[i]=='S')s_turn(); 45 for(int i=l;i<r;++i)for(int j=f;j<b;++j)printf("%d ",i);puts(""); 46 for(int i=l;i<r;++i)for(int j=f;j<b;++j)printf("%d ",j);puts(""); 47 printf("%d\n",mxt); 48 } 49 }
T2:數字
比較神仙。
高精還是要打的,但是只需要讀入,除2和5的倍數的低精數,模同理,以及大於號。。。
模的話直接取最低位返回就行。。。emm我是萬進制的
設Ext(a,b)是b除去所有因子a后剩下的數,那么題目就是求Ext(10,n!)%10k
直覺,可以CRT。分成2和5處理。
絕大多數情況下因子2都嚴格比5多,所以Ext(10,n!)%2==0
現在只需要求出Ext(5,n!)%10k
那么分解1000就是8×125。對於8其因子數也很多所以最后乘逆元。
問題就變成求Ext mod125的答案了。
可以把階乘里能整除5的和不能的分開考慮,而能被整除的部分就是Ext(5,(n/5)!),遞歸處理。
可以發現Ext之后階乘操作其實是循環的,因為mod125所以每125位就循環了。
循環的部分可以快速冪處理。剩余部分可以預處理。
我知道這作為一個題解過於草率,沒時間了溜了。

1 #include<cstdio> 2 #include<cstring> 3 #include<iostream> 4 using namespace std; 5 char s[105];int l,k;const int mod[4]={1,10,100,1000},m5[4]={1,5,25,125};int fac[133],FAC[133]; 6 struct bigint{ 7 int a[102],ws; 8 void get(){ 9 ws=(l-1)/4+1;for(int i=0;i<=100;++i)a[i]=0; 10 for(int i=1;i<ws;++i)a[i]=s[l-4*i]*1000+s[l-4*i+1]*100+s[l-4*i+2]*10+s[l-4*i+3]; 11 for(int i=1;i<=(l-1)%4+1;++i)a[ws]=a[ws]*10+s[i-1]; 12 } 13 void operator/=(int k){ 14 for(int i=ws;i;--i)a[i-1]+=a[i]%k*10000,a[i]/=k; 15 while(!a[ws]&&ws)ws--; 16 } 17 int operator%(int k){return a[1]%k;} 18 bool operator>(int k){return ws>1||a[1]>k;} 19 }n,m; 20 int pow(int b,int t,int mod,int a=1){for(;t;t>>=1,b=b*b%mod)if(t&1)a=a*b%mod;return a;} 21 int Ext(bigint n){ 22 if(n>125);else return fac[n.a[1]]; 23 int x=n%125;n/=5;int K=Ext(n);n/=25; 24 return K*pow(FAC[125],n%100,125)%125*FAC[x]%125; 25 } 26 void put(int x,int k){for(int i=k;i;--i)if(x%mod[i]/mod[i-1]==0)putchar(48);else break;printf("%d\n",x%mod[k]);} 27 int main(){//freopen("t2.in","r",stdin);freopen("t2.out","w",stdout); 28 fac[0]=FAC[0]=1;for(int i=1;i<=125;++i){int j=i;while(j%5==0)j/=5;fac[i]=fac[i-1]*j%125;FAC[i]=FAC[i-1]*(i%5==0?1:i)%125;} 29 int ans,t,tot;scanf("%d",&t); 30 while(t--){ 31 scanf("%s%d",s,&k);l=strlen(s); 32 for(int i=0;i<l;++i)s[i]-=48; 33 n.get();ans=Ext(n); 34 if(l==1&&n.a[1]<=6){int a=1;for(int i=1;i<=n.a[1];++i)a*=i;if(a%10==0)a/=10;put(a,k);continue;} 35 m=n;tot=0; 36 while(m.ws)m/=5,(tot+=m%100)%=100; 37 ans*=pow(63,tot,125);ans%=125; 38 for(int i=0;i<1000;i+=8)if(i%125==ans)put(i,k); 39 } 40 }
T3:甜圈
考察的思路很不錯啊。
因為不能多不能少不能亂序,所以很符合字符串的性質。
因為要區間操作,所以方便快捷的hash。
那么就變成了區間加區間乘的線段樹啦!
(居然還有人不會線段樹板子%%%)

1 #include<cstdio> 2 int cl[800005],cr[800005],ans; 3 unsigned long long hsh[800005],lzm[800005],lza[800005],HSH; 4 void build(int p,int l,int r){ 5 cl[p]=l;cr[p]=r;lzm[p]=1; 6 if(l==r)return; 7 build(p<<1,l,l+r>>1);build(p<<1|1,(l+r>>1)+1,r); 8 } 9 void down(int p){ 10 hsh[p<<1]*=lzm[p];hsh[p<<1|1]*=lzm[p]; 11 lzm[p<<1]*=lzm[p];lzm[p<<1|1]*=lzm[p]; 12 lza[p<<1]*=lzm[p];lza[p<<1|1]*=lzm[p]; 13 hsh[p<<1]+=lza[p];hsh[p<<1|1]+=lza[p]; 14 lza[p<<1]+=lza[p];lza[p<<1|1]+=lza[p]; 15 lza[p]=0;lzm[p]=1; 16 } 17 void chg(int p,int l,int r,int w){ 18 if(l<=cl[p]&&cr[p]<=r){hsh[p]=hsh[p]*29+w;lza[p]*=29;lzm[p]*=29;lza[p]+=w;return;} 19 if(lza[p]||lzm[p]!=1)down(p); 20 if(l<=cr[p<<1])chg(p<<1,l,r,w); 21 if(r>=cl[p<<1|1])chg(p<<1|1,l,r,w); 22 } 23 void ask(int p){ 24 if(cl[p]==cr[p]){ans+=HSH==hsh[p];return;} 25 if(lza[p]||lzm[p]!=1)down(p); 26 ask(p<<1);ask(p<<1|1); 27 } 28 int main(){ 29 int n,t,l,r,w,k; 30 scanf("%d%d%d",&n,&k,&t); 31 build(1,1,n); 32 while(t--)scanf("%d%d%d",&l,&r,&w),chg(1,l,r,w); 33 for(int i=1;i<=k;++i)HSH=HSH*29+i; 34 ask(1);printf("%d\n",ans); 35 }