此做法是否为假的
查看原帖
此做法是否为假的
895690
gghack_Nythix楼主2024/7/20 09:20

rt,我按照常规的方法(只给二进制位相差为1的点连边,这样子什么点都能凑出来)写了一份代码,结果发现过不了第一个样例,我尝试给起点到每一个其他的点都连了一条边,就突然AC了?

#include<bits/stdc++.h>
#define int long long
using namespace std;
int n,m,c;
struct node {
	int v,w;
	bool operator < (const node & hh) const {return w > hh.w;}
};
vector<node>g[2000005];
int dis[2000005];
bool vis[2000005];
void dijkstra(int st,int ed) {
	for(int i = 1;i <= n;++i) dis[i] = 1e18;
	priority_queue<node>q;
	dis[st] = 0;
	q.push(node{st,0});
	while(!q.empty()) {
		node tp = q.top();
		q.pop();
		if(vis[tp.v]) continue;
		vis[tp.v] = 1;
		for(auto x : g[tp.v]) {
			if(dis[x.v] > dis[tp.v] + x.w){
				dis[x.v] = dis[tp.v] + x.w;
				q.push(node{x.v,dis[x.v]});
			}
		}
	}
	cout << dis[ed] << '\n';
	return ;
}
signed main(){
	cin >> n >> m >> c;
	for(int i = 1;i <= m;++i) {
		int u,v,w;
		cin >> u >> v >> w;
		g[u].push_back(node{v,w});
	}
	for(int i = 1;i <= n;++i){
		for(int j = 0;j <= 21;++j) {
			int o = (i ^ (1 << j));
			if(o <= n)g[i].push_back(node{o,(1 << j) * c});
		}
	} 
	int a,b;
	cin >> a >> b;
	for(int i = 1;i <= n;++i) g[a].push_back(node{i,(i ^ a) * c});//开始的代码没有这一句。
	dijkstra(a,b);
	return 0;
}
2024/7/20 09:20
加载中...