模拟赛

以后不给题解的模拟赛,死也不做,
我这么菜,你还不给我题解

T1不会
没题解,std不懂
trick还是太菜,唉
自己想的大概是
枚举每个点处理包含的矩阵,展开平方,对于拆除改点的部分维护前缀和,这个前缀和类似与带一个二项式容斥的和式
然后对于另一部分可以把矩阵分治
在合并的时候维护一下矩形的匹配轮廓
WA,可能那个地方没处理或没考虑到吧....

#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<cstdlib>
using namespace std;
typedef long long ll;
typedef long double ld;
typedef pair<int,int> pr;
const double pi=acos(-1);
#define rep(i,a,n) for(int i=a;i<=n;i++)
#define per(i,n,a) for(int i=n;i>=a;i--)
#define Rep(i,u) for(int i=head[u];i;i=Next[i])
#define clr(a) memset(a,0,sizeof a)
#define pb push_back
#define mp make_pair
#define putk() putchar(' ')
ld eps=1e-9;
ll pp=1000000007;
ll mo(ll a,ll pp){if(a>=0 && a<pp)return a;a%=pp;if(a<0)a+=pp;return a;}
ll powmod(ll a,ll b,ll pp){ll ans=1;for(;b;b>>=1,a=mo(a*a,pp))if(b&1)ans=mo(ans*a,pp);return ans;}
ll gcd(ll a,ll b){return (!b)?a:gcd(b,a%b);}
ll read(){
	ll ans=0;
	char last=' ',ch=getchar();
	while(ch<'0' || ch>'9')last=ch,ch=getchar();
	while(ch>='0' && ch<='9')ans=ans*10+ch-'0',ch=getchar();
	if(last=='-')ans=-ans;
	return ans;
}
void put(ll a){
	if(a<0)putchar('-'),a=-a;
	int top=0,q[20];
	while(a)q[++top]=a%10,a/=10;
	top=max(top,1);
	while(top--)putchar('0'+q[top+1]);
}
//head
#define N 3100 
#define int long long 
ll a[N][N];
bool p[N][N];
int b[N][N];
int n;
const int xt[]={0,1,0,-1};
const int yt[]={1,0,-1,0};
main(){ 
	freopen("matrix.in","r",stdin); freopen("matrix.out","w",stdout); 
	n=read();
	int x=1,y=1,k=0;
	int tot=1;
	rep(i,1,n)
		rep(j,1,n)p[i][j]=1;
	rep(i,1,n*n){
		b[x][y]=tot;
		p[x][y]=0;
		if(i==n*n)break;
		++tot;

		while(!p[x+xt[k]][y+yt[k]])k=(k+1)%4;
		x+=xt[k];
		y+=yt[k];
	}
	ll ans=0;
	rep(i,1,n)
		rep(j,1,n){
			ll t=b[i][j];
			ans=mo(ans-t*i*j%pp*t%pp*(n-i+1)%pp*(n-j+1),pp);
			a[i][j]=mo(b[i][j]*i%pp*j%pp+a[i-1][j]+a[i][j-1]-a[i-1][j-1],pp);
			ans=(ans+2*a[i][j]*t%pp*(n-i+1)%pp*(n-j+1)%pp)%pp;
		}
	rep(i,1,n)
		per(j,n,1){
			ll t=b[i][j];
			a[i][j]=mo(b[i][j]*i%pp*(n-j+1)+a[i-1][j]+a[i][j+1]-a[i-1][j+1],pp);
			ans=(ans+2*a[i-1][j+1]*t%pp*(n-i+1)%pp*j)%pp;
		}	
	cout<<ans;
	return 0;
}

T2
二分,单调队列维护最大最下,盼区间个数瞎写

#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<cstdlib>
using namespace std;
typedef long long ll;
typedef long double ld;
typedef pair<int,int> pr;
const double pi=acos(-1);
#define rep(i,a,n) for(int i=a;i<=n;i++)
#define per(i,n,a) for(int i=n;i>=a;i--)
#define Rep(i,u) for(int i=head[u];i;i=Next[i])
#define clr(a) memset(a,0,sizeof a)
#define pb push_back
#define mp make_pair
#define putk() putchar(' ')
ld eps=1e-9;
ll pp=1000000007;
ll mo(ll a,ll pp){if(a>=0 && a<pp)return a;a%=pp;if(a<0)a+=pp;return a;}
ll powmod(ll a,ll b,ll pp){ll ans=1;for(;b;b>>=1,a=mo(a*a,pp))if(b&1)ans=mo(ans*a,pp);return ans;}
ll gcd(ll a,ll b){return (!b)?a:gcd(b,a%b);}
ll read(){
	ll ans=0;
	char last=' ',ch=getchar();
	while(ch<'0' || ch>'9')last=ch,ch=getchar();
	while(ch>='0' && ch<='9')ans=ans*10+ch-'0',ch=getchar();
	if(last=='-')ans=-ans;
	return ans;
}
void put(ll a){
	if(a<0)putchar('-'),a=-a;
	int top=0,q[20];
	while(a)q[++top]=a%10,a/=10;
	top=max(top,1);
	while(top--)putchar('0'+q[top+1]);
}
//head
#define N 410000
int a[N],q1[N],q2[N];
ll k;
int n;
bool check(int kk){
	int l1=1,r1=1,l2=1,r2=1;
	q1[1]=1;q2[1]=1;
	int z=1;
	ll ans=0;
	if(kk==1)ans=1;
	else ans=0;
	rep(i,2,n){
		while(l1<=r1 && a[q1[r1]]>=a[i])--r1;
		q1[++r1]=i;
		while(l2<=r2 && a[q2[r2]]<=a[i])--r2;
		q2[++r2]=i;
		while(z<i){
				int t1=l1,t2=l2;
				++z;
				while(q1[t1]<z)++t1;
				while(q2[t2]<z)++t2;
				if(a[q2[t2]]-a[q1[t1]]>=kk){
					l1=t1;
					l2=t2;
				}
				else{
					--z;
					break;
				}
		}
		if(a[q2[l2]]-a[q1[l1]]>=kk)ans+=z;
	}
	return ans>=k;
}
int main(){
	freopen("kth.in","r",stdin);
	freopen("kth.out","w",stdout);
	n=read();k=read();
	rep(i,1,n)a[i]=read();
	int l=0,r=1000000000;
	while(l<r){
		int mid=(l+r+1)/2;
		if(check(mid))l=mid;
		else r=mid-1;
	}
	cout<<l<<endl;
	return 0;
	return 0;
}

T3
树上哈希判断同构

#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<cstdlib>
#include<map>
using namespace std;
typedef long long ll;
typedef long double ld;
typedef pair<int,int> pr;
const double pi=acos(-1);
#define rep(i,a,n) for(int i=a;i<=n;i++)
#define per(i,n,a) for(int i=n;i>=a;i--)
#define Rep(i,u) for(int i=head[u];i;i=Next[i])
#define clr(a) memset(a,0,sizeof a)
#define pb push_back
#define mp make_pair
#define putk() putchar(' ')
ld eps=1e-9;
ll p1=1000000007;
ll p2=1000000009;
ll mo(ll a,ll pp){if(a>=0 && a<pp)return a;a%=pp;if(a<0)a+=pp;return a;}
ll powmod(ll a,ll b,ll pp){ll ans=1;for(;b;b>>=1,a=mo(a*a,pp))if(b&1)ans=mo(ans*a,pp);return ans;}
ll gcd(ll a,ll b){return (!b)?a:gcd(b,a%b);}
ll read(){
	ll ans=0;
	char last=' ',ch=getchar();
	while(ch<'0' || ch>'9')last=ch,ch=getchar();
	while(ch>='0' && ch<='9')ans=ans*10+ch-'0',ch=getchar();
	if(last=='-')ans=-ans;
	return ans;
}
void put(ll a){
	if(a<0)putchar('-'),a=-a;
	int top=0,q[20];
	while(a)q[++top]=a%10,a/=10;
	top=max(top,1);
	while(top--)putchar('0'+q[top+1]);
}
//head
#define N 210000
map<ll,bool>G1,G2;
int head[N],q[N],fa[N][20],v[N],num,next[N],dep[N],len1,len2,n,m;
char str[N];
ll b1[N],inv1[N],hash1_1[N][26],hash2_1[N][26],ans[2][26];
ll b2[N],inv2[N],hash1_2[N][26],hash2_2[N][26],ans2[2][26];
bool vis[N];
int f[26];
void add(int x,int y){
	v[++num]=y;next[num]=head[x];head[x]=num;
}
void bfs(){
	int t=0,w=1;
	q[1]=1;
	vis[1]=1;
	hash1_1[1][str[1]-'a']=hash2_1[1][str[1]-'a']=1;
	hash1_2[1][str[1]-'a']=hash2_2[1][str[1]-'a']=1;
	while(t<w){
		int u=q[++t];
		for(int i=1;(1<<i)<=dep[u];i++)fa[u][i]=fa[fa[u][i-1]][i-1];
		for(int i=head[u];i;i=next[i])
			if(!vis[v[i]]){
				vis[v[i]]=1;
				q[++w]=v[i];
				fa[v[i]][0]=u;
				dep[v[i]]=dep[u]+1;
				rep(j,0,25){
				hash1_1[v[i]][j]=(hash1_1[u][j]*31+((str[v[i]]-'a')==j))%p1;
				hash2_1[v[i]][j]=(hash2_1[u][j]+b1[dep[v[i]]]*((str[v[i]]-'a')==j))%p1;
				hash1_2[v[i]][j]=(hash1_2[u][j]*37+((str[v[i]]-'a')==j))%p2;
				hash2_2[v[i]][j]=(hash2_2[u][j]+b2[dep[v[i]]]*((str[v[i]]-'a')==j))%p2;
				}
			}
	}
}
int lca(int x,int y){
	if(dep[y]>dep[x])swap(x,y);
	for(int i=18;i>=0;i--)
		if(dep[x]-(1<<i)>=dep[y])x=fa[x][i];
	if(x==y)return x;
	for(int i=18;i>=0;i--)
		if(fa[x][i]!=fa[y][i])x=fa[x][i],y=fa[y][i];
	return fa[x][0];
}

int find(int x){
	if(x==f[x])return x;
	return f[x]=find(f[x]);
}
ll work1_1(int x,int y,int k){
	return mo(hash1_1[y][k]-hash1_1[fa[x][0]][k]*b1[dep[y]-dep[x]+1],p1);
}
ll work2_1(int x,int y,int k){
	return mo(hash2_1[x][k]-hash2_1[fa[y][0]][k],p1)*inv1[dep[y]]%p1;
}
ll work1_2(int x,int y,int k){
	return mo(hash1_2[y][k]-hash1_2[fa[x][0]][k]*b2[dep[y]-dep[x]+1],p2);
}
ll work2_2(int x,int y,int k){
	return mo(hash2_2[x][k]-hash2_2[fa[y][0]][k],p2)*inv2[dep[y]]%p2;
}
void work(int x,int y,int len,ll *ans1,ll *ans2){
	int z=lca(x,y);
	len=dep[x]-dep[z]+dep[y]-dep[z]+1;
	rep(i,0,25){
		ans1[i]=mo(work1_1(z,y,i)+work2_1(x,z,i)*b1[dep[y]-dep[z]]-((str[z]-'a')==i)*b1[dep[y]-dep[z]],p1);
		ans2[i]=mo(work1_2(z,y,i)+work2_2(x,z,i)*b2[dep[y]-dep[z]]-((str[z]-'a')==i)*b2[dep[y]-dep[z]],p2);
	}
	rep(i,0,25)
		if(find(i)!=i){
			ans1[find(i)]=(ans1[find(i)]+ans1[i])%p1,ans1[i]=0;
			ans2[find(i)]=(ans2[find(i)]+ans2[i])%p2,ans2[i]=0;
		}
}
bool check(){
	if(len1!=len2)return 0;
	ll tot1=0,tot2=0,s1=0,s2=0,rec1=0,rec2=0;
	rep(i,0,25){
	//	printf("%I64d %I64d %I64d %I64d
",ans[0][i],ans[1][i],ans2[0][i],ans2[1][i]);
		if(ans[0][i]!=ans[1][i])++tot1,rec1=mo(ans[0][i]-ans[1][i],p1);
		if(ans2[0][i]!=ans2[1][i])++tot2,rec2=mo(ans2[0][i]-ans2[1][i],p2);
	}
	if(tot1!=0 && tot1!=2)return 0;
	if(tot2!=0 && tot2!=2)return 0;
	if(tot1==0 && tot2==0)return 1;
	return G1[rec1] && G2[rec2];
}
char ss[100];
int main(){
	freopen("string.in","r",stdin);
	freopen("string.out","w",stdout);
	n=read();m=read();
	scanf("%s",str+1);
	rep(i,2,n){
		int x=read(),y=read();
		add(x,y);
		add(y,x);
	}
	b1[0]=1;
	rep(i,1,n)b1[i]=b1[i-1]*31%p1;
	inv1[0]=1;
	inv1[1]=powmod(31,p1-2,p1);
	rep(i,2,n)inv1[i]=inv1[i-1]*inv1[1]%p1;
	rep(i,0,n)G1[b1[i]]=1,G1[mo(-b1[i],p1)]=1;
	
	b2[0]=1;
	rep(i,1,n)b2[i]=b2[i-1]*37%p2;
	inv2[0]=1;
	inv2[1]=powmod(37,p2-2,p2);
	rep(i,2,n)inv2[i]=inv2[i-1]*inv2[1]%p2;
	G1[0]=1;G2[0]=1;
	rep(i,0,n)G2[b2[i]]=1,G2[mo(-b2[i],p2)]=1;
	bfs();
/*	cout<<dep[6]<<endl;
	cout<<hash1[1][0]<<endl;
	cout<<hash1[8][0]<<endl;
	cout<<hash1[6][0]<<endl;
	cout<<work1(1,6,0)<<endl;*/
	while(m--){
		int kk=read(),l1=read(),r1=read(),l2=read(),r2=read();
		rep(i,0,25)ans[0][i]=ans[1][i]=0;
		rep(i,0,25)ans2[0][i]=ans2[1][i]=0;
		rep(i,0,25)f[i]=i;
		while(kk--){
			scanf("%s",ss);
			f[find(ss[0]-'a')]=find(ss[1]-'a');
		}
		work(l1,r1,len1,ans[0],ans2[0]);
		work(l2,r2,len2,ans[1],ans2[1]);
		if(check())puts("YES");
		else puts("NO");
	}
	return 0;
}

原文地址:https://www.cnblogs.com/sssy/p/9439380.html