NEUQ-ACM预备队必做题06

但是真的是06吗

P3367 【模板】并查集

压缩路径

#include<bits/stdc++.h>
#define f(i,a,b) for(int (i)=(a);(i)<=(b);++i)
#define bitlow(a) ((a)&-1*(a))
#define Ma(x,y) make_pair((x),(y))
using namespace std;

const int N=10001;
int f[N];

int fa(int x)
{
	if(f[x]!=x){
		f[x]=fa(f[x]);
		
	}
	return f[x];
}
void merge(int x,int y)
{
	int fa1=fa(x),fa2=fa(y);
	if(fa1!=fa2)
	{
		f[fa1]=fa2;
	}
	return;
}

int main()
{
	ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
	int n,m;
	cin>>n>>m;
	//initial
	f(i,1,n)
	  f[i]=i;
	  
	f(i,1,m){
		int a,b,c;
		cin>>a>>b>>c;
		if(a==1){
			merge(b,c);
			continue;
		}
		if(fa(b)==fa(c))
	    	cout<<'Y'<<'\n';
		else
		    cout<<'N'<<'\n';
	}
	  
} 

P8604 [蓝桥杯 2013 国 C] 危险系数

暴力枚举每个点取消的情况,bfs判断是否可以联通,ans=总的点数-去掉后仍然可以联通的点数

#include<bits/stdc++.h>
#define f(i,a,b) for(int (i)=(a);(i)<=(b);++i)
#define bitlow(a) ((a)&-1*(a))
#define Ma(x,y) make_pair((x),(y))
using namespace std;

const int N=1001,M=2001;
int nex[M],to[M],fr[N],cnt=0,pd[N];
int n,m,ans=0,con[N],vis[N];
int st,en,flag;
inline void add(int x,int y)
{
	++cnt;
	nex[cnt]=fr[x];
	to[cnt]=y;
	fr[x]=cnt;
}
void bfs(int x)
{
	if(x==en){
	  return;
	}	
    queue<int> q;
    q.push(x);
    while(!q.empty())
    {
    	int cur=q.front();
    	if(cur==en){
	      --ans;
//	      cout<<"threat"<<endl;//********
	      return;
	    }
    	q.pop();
    	//if(vis[cur]) continue;
    	vis[cur]=1;
//    	cout<<endl<<"now is "<<cur<<" to be found"<<endl;
	    for(int i=fr[cur];i;i=nex[i])
	    {
	  	    if(con[to[i]]||vis[to[i]]){
//	  	    	cout<<" as "<<to[i]<<" is labeled "; 
	  	    	continue;
			  } 
	  	    q.push(to[i]);	 
		    vis[to[i]]=1;  	
//			cout<<to[i]<<" ";  //***********
	    }
//	    cout<<endl;
	}
	return;  
}
int main()
{
	ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
	cin>>n>>m;
	f(i,1,m){
		int a,b;
		cin>>a>>b;
		add(a,b);
		add(b,a);
	}
	cin>>st>>en;
	ans=n-2;// st&&en
	
	f(k,1,n){
		if(k==st||k==en)
		    continue; 
//		cout<<"close "<<k<<endl;//***********	 
		con[k]=1;
		for(int i=fr[st];i;i=nex[i]){
	  	    if(con[to[i]]) continue;
	  	    flag=0;
	  	    memset(vis,0,sizeof(vis));
	  	    vis[st]=1;
	  	    bfs(to[i]);
	    }	
	  con[k]=0;
	}
	cout<<ans;
	return 0;  
} 

P1330 封锁阳光大学

染色

#include<bits/stdc++.h>
#define f(i,a,b) for(int (i)=(a);(i)<=(b);++i)
#define bitlow(a) ((a)&-1*(a))
#define Ma(x,y) make_pair((x),(y))
using namespace std;

const int N=100001,M=200001;
int nex[M],to[M],fr[N],cnt=0;
int n,m,ans=0;
int flag,color[N],used[N];
int sum[4];
inline void add(int x,int y)
{
	++cnt;
	nex[cnt]=fr[x];
	to[cnt]=y;
	fr[x]=cnt;
}
inline void dfs(int x,int c)
{
	if(used[x]){
		if(color[x]!=c){
			flag=1;
		}
			
		return;
	}
	color[x]=c;
	++sum[1-c];
	used[x]=1;
    for(int i=fr[x];i;i=nex[i])
		dfs(to[i],-1*c); 
 	
	return;
}
int main()
{
	ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
	cin>>n>>m;
	f(i,1,m){
		int a,b;
		cin>>a>>b;
		add(a,b);
		add(b,a);
	}
	
	f(i,1,n){
		if(flag){
			cout<<"Impossible";
			return 0;
		}
		if(used[i]) continue;
		sum[2]=0,sum[0]=0;
		dfs(i,1);
		ans+=min(sum[0],sum[2]);
	}
	cout<<ans;
	return 0;   
} 

P3916 图的遍历

反向建图

#include<bits/stdc++.h>
#define f(i,a,b) for(int (i)=(a);(i)<=(b);++i)
#define bitlow(a) ((a)&-1*(a))
#define Ma(x,y) make_pair((x),(y))
using namespace std;

const int N=100001,M=200001;
int n,m,ans;
int cnt=0,nex[M],fr[N],to[M],vis[N];
int mmax[N];//dp
inline void add(int x,int y)
{
	++cnt;
	nex[cnt]=fr[x];
	to[cnt]=y;
	fr[x]=cnt;
	return;
}
inline void find(int x)
{
    if(vis[x])
	    return; 
	vis[x]=1;    
	for(int i=fr[x];i;i=nex[i]){
		if(vis[to[i]]) 
			continue;
		mmax[to[i]]=ans;
		find(to[i]);
	}
} 
int main()
{
	ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
	cin>>n>>m;
 	f(i,1,m){
 		int a,b;
 		cin>>a>>b;
 		add(b,a);//反向建图 
	}
 	for(int i=n;i>0;--i){
 		ans=i;
 		if(mmax[i]==0) mmax[i]=i;
 		find(i);
	 }
 	f(i,1,n){
 		cout<<mmax[i]<<" ";
	 }	
	return 0;   
} 

P1119 灾后重建

floyed

注意点的更新在时间变化。往后更新

#include<bits/stdc++.h>
#define f(i,a,b) for(int (i)=(a);(i)<=(b);++i)
#define bitlow(a) ((a)&-1*(a))
#define Ma(x,y) make_pair((x),(y))
using namespace std;

const int N=201,M=200001,INF=1e8;
int n,m,ans;
int cnt=0,nex[M],fr[N],to[M],vis[N],v[M];
int ti[N],dis[N][N],diss[N][N];
int k=0;
void error(){
	    cout<<'/n';
		for(int i=0;i<n;++i){
		  for(int j=0;j<n;++j)
		  		if(dis[i][j]<INF) 
					cout<<dis[i][j]<<" ";
				else
					cout<<-1<<" ";	
			cout<<'\n';	
		} 	
}
inline void floyed(int t)
{
	for(;k<n;++k){
		if(ti[k]>t) 
			return;
			
		f(i,0,n-1){
		//	if(ti[i]>t) break;
			f(j,0,n-1){
				if(i==j) continue;
		//		    if(ti[j]>t) break;
		//			if(t==4&&k==3&&i==0&&j==1)  cout<<dis[i][j]<<" quick "<<dis[i][k]+dis[k][j]<<endl;
					dis[i][j]=min(dis[i][k]+dis[k][j],dis[i][j]);
				
				}
			}	
		}
	return;	
}
 
int main()
{
	ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
	cin>>n>>m;
	f(i,0,n-1)
		f(j,0,n-1){
			dis[i][j]=1e9;
			diss[i][j]=1e9;
		}
			
		
	for(int i=0;i<n;++i){
		cin>>ti[i];
		dis[i][i]=0;
		diss[i][i]=0;
	}
	 
 	f(i,1,m){
 		int a,b,c;
 		cin>>a>>b>>c;
 		dis[a][b]=dis[b][a]=c;
	} 
	//error();
	int q;
	cin>>q;
	
 	while(q--){
 		int a,b,c;
 		cin>>a>>b>>c;
 		//if(c>=ti[k])
 		floyed(c);
 		if(ti[a]>c||ti[b]>c){
 			cout<<-1<<'\n';	
 			continue;
		 }
 		if(dis[a][b]<INF)
 			cout<<dis[a][b]<<'\n';
 		else
		 	cout<<-1<<'\n';	 
	}
	return 0;   
} 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值