L2-002 連結串列去重(複習)

YuKiCheng發表於2024-04-20
#include <bits/stdc++.h>
using namespace std;
const int inf = 0x3f3f3f3f;
#define ll long long
int dist[510];
int edges[510][510];
bool check[510]; 
int nums[510];//救援隊人數
int values[510];
int pre[510];
int cnt[510]; 
void dijkstra(int dist[],int n,int start){//記得初始化
    values[start]=nums[start]; 
	cnt[start]=1;
	dist[start]=0;
	for(int i=0;i<n;i++){
		int minv=inf,minx;
		for(int j=0;j<n;j++){
			if(!check[j] && dist[j]<minv){
				minv=dist[j];
				minx=j;
			}
		}
		check[minx]=1;
		for(int j=0;j<n;j++){
			if(minv+edges[minx][j]<dist[j]){
				dist[j]=minv+edges[minx][j];
				pre[j]=minx;
				values[j]=values[minx]+nums[j];
				cnt[j]=cnt[minx];
			}else if(minv+edges[minx][j]==dist[j]){
                cnt[j]+=cnt[minx];
				if(values[j]<values[minx]+nums[j]){
					pre[j]=minx;
					values[j]=values[minx]+nums[j];
				}				
			}
		}
	}
}
int main(){
	memset(edges,0x3f,sizeof(edges));
	memset(dist,0x3f,sizeof(dist));
	memset(pre,-1,sizeof(pre));
	int n,m,s,d;
	cin>>n>>m>>s>>d;
	for(int i=0;i<n;i++){
		cin>>nums[i];
	} 
	for(int i=0;i<m;i++){
		int a,b,c;
		cin>>a>>b>>c;
		edges[a][b]=c;
		edges[b][a]=c;
	}
	dijkstra(dist,n,s);
	cout<<cnt[d]<<" "<<values[d]<<'\n';
	vector<int> vec;
	int x=d;
	vec.push_back(x);
	while(pre[x]!=-1){
		vec.push_back(pre[x]);
		x=pre[x];
	}
	int count=0;
	for(int i=vec.size()-1;i>=0;i--){
		if(count) cout << " ";
		cout<<vec[i];
		count++;
	}
	return 0;
}

相關文章