CodeForces-20C Dijkstra? (最短路-Dijkstra堆优化版)

题目链接

题意:给出n个点,m条边,求1到n的最短距离的路径.

题解:,大数据,不可使用Dijkstra邻接矩阵和邻接表,都卡空间和时间,直接上堆优化的最短路模板即可~

代码如下:

#include
#include
#include
#include
#include
#include
#include
#include
#include
using namespace std;
#define ll long long
#define inf 0x3f3f3f3f
const int maxn = 1e5 + 10;
struct edge {//边
	int u, v, w;
	edge() {}
	edge(int uu, int vv, int ww) {
		u = uu;
		v = vv;
		w = ww;
	}
};
struct node {//点
	int from, i, w;  //from=前驱点,i=当前点,w=起点到当前点最短距离
	node() {}
	node(int pp, int ii, int ww) {
		from = pp;
		i = ii;
		w = ww;
	}
	bool operator <(const node &a)const {
		return a.w < w;
	}
};
vectorv[maxn];
bool vis[maxn];
int dis[maxn];   //dis[],pre[]看题目要求加
int pre[maxn];
int n;
int dijsktra(int s, int t) {
	priority_queueq;
	q.push(node(0, s, 0));
	memset(vis, 0, sizeof(vis));
	while (!q.empty()) {
		node p = q.top();
		q.pop();
		if (p.i == t) {//采用优先队列写法,故当添加该t(终点)时得到的就是最短路了
			pre[p.i] = p.from;
			dis[p.i] = p.w;
			return p.w;
		}
		if (vis[p.i]) continue;  //访问过跳过
		dis[p.i] = p.w;     //可以存到各个点的最短距离
		pre[p.i] = p.from;   //记录前驱
		vis[p.i] = true;
		for (int i = 0; i < v[p.i].size(); i++) {
			edge &e = v[p.i][i];
			if (vis[e.v]) continue;
			q.push(node(e.u, e.v, p.w + e.w));
		}
	}
	return -1;
}
void dfs(int t, int x, int cnt) { //当前点x到起点t的最短路径
	if (pre[x] != 0) {
		dfs(t, pre[x], cnt + 1);
		printf("%d%c", x, cnt == 1 ? '\n' : ' ');
	}
	else
		printf("%d%c", t, ' ');
}
int main() {
	int  m;
	while (~scanf("%d%d", &n, &m)) {
		memset(pre, 0, sizeof(pre));   //初始化
		for (int i = 1; i <= n; i++)
			v[i].clear();
		while (m--) {//添加无向边
			int uu, vv, ww;
			scanf("%d%d%d", &uu, &vv, &ww);
			v[uu].push_back(edge(uu, vv, ww));
			v[vv].push_back(edge(vv, uu, ww));
		}
		if (dijsktra(1, n) != -1)
			dfs(1, n, 1);   //输出
		else
			cout << "-1" << endl;
	}
}


 

你可能感兴趣的:(最短路,ACM,算法,Codeforces,堆优化的最短路)