UNAC 100pts,#11MLE求调
查看原帖
UNAC 100pts,#11MLE求调
477821
toolong114514楼主2024/5/6 18:35
#include<iostream>
#include<cstring>
#include<queue>
using namespace std;
#define int long long
const int INF=0x3f3f3f3f3f3f3f3f;
const int N=5e5+10;
struct node{
	signed to,nxt,val;
}edge[N];
signed head[N/5];
signed cnt;
void add(int u,int v,int w){
	edge[++cnt]={v,head[u],w};
	head[u]=cnt; 
}
struct ccf{
	int pos,val;
	friend bool operator<(ccf pre,ccf nxt){
		return pre.val>nxt.val;
	}
};
priority_queue<ccf> q;
int ans[N/5];signed cit[N/5];
signed n,m,k,fm;int anss=INF;
int dij(){
	while(!q.empty()) q.pop();
	for(int i=1;i<n+3;i++){
		ans[i]=INF;
	}
	ans[n+1]=INF;
	q.push({n+1,0});
	while(!q.empty()){
		ccf now=q.top();
		q.pop();
		if(ans[now.pos]<now.val) continue;
		ans[now.pos]=now.val;
		for(int i=head[now.pos];i!=-1;i=edge[i].nxt){
			if(ans[edge[i].to]>now.val+edge[i].val){
				q.push({edge[i].to,now.val+edge[i].val});
			}
		}
	}
	return ans[n+2];
}
signed t;
void back_to(){
	cnt=fm;
	for(int i=1;i<=n;i++){
		if(edge[head[i]].to==n+2) head[i]=edge[head[i]].nxt;
	} 
	head[n+1]=-1;
}
signed main(){
	//memset(head,-1,sizeof(head));
	ios::sync_with_stdio(false);
	cin>>t;
	while(t--){
		cnt=0;
		anss=INF;
		cin>>n>>m>>k;
		for(int i=1;i<n+3;i++){
			head[i]=-1;
			ans[i]=INF;
		}
		while(m--){
			int x,y,z;
			cin>>x>>y>>z;
			add(x,y,z);
		}
		fm=cnt;
		signed sb=0;
		for(int i=1;i<=k;i++){
			cin>>cit[i];
			sb=max(sb,cit[i]);
		}
		for(int i=0;i<21;i++){
			if((1<<i)>sb) break;
			for(int j=1;j<=k;j++){
				if(cit[j]&(1<<i)) add(n+1,cit[j],0);
				else add(cit[j],n+2,0);
			}
			anss=min(anss,dij());
			back_to();
		}	
		for(int i=0;i<21;i++){
			if((1<<i)>sb) break;
			for(int j=1;j<=k;j++){
				if(cit[j]&(1<<i)) add(cit[j],n+2,0);
				else add(n+1,cit[j],0);
			}	
			anss=min(anss,dij());
			back_to();
		}
		cout<<anss<<'\n';
	}
	return 0;
}
2024/5/6 18:35
加载中...