D. Complete The Graph
Solution
特判掉原本最短路(没有加入0边)<l→"NO"
分析一下,s→t的最短路,贪心,加入0边,先不管取值,先一条条赋为1(最小positive integer),如果当前最短路<l是不是说明当前这条边是最短路的一部分,所以答案就出来了,将这条边赋值为l-d[t]+1,如果最短路仍>l,而这已经是这条边的最优贡献,所以赋值为1继续做.
然后注意一下细节即可(WA了4发~~)
复杂度:O(nmlogn)(优化:对了,每次做最短路,当前值已经>l可以直接退出,所以其实跑得很快296MS)
// This file is made by YJinpeng,created by XuYike's black technology automatically.
// Copyright (C) 2016 ChangJun High School, Inc.
// I don't know what this program is.
#include <iostream>
#include <vector>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <queue>
#define IN inline
#define RG register
#define MOD 1000000007
#define INF 1e9+1
using namespace std;
typedef long long LL;
const int MAXN=1010;
const int MAXM=20010;
inline int gi() {
register int w=0,q=0;register char ch=getchar();
while((ch<'0'||ch>'9')&&ch!='-')ch=getchar();
if(ch=='-')q=1,ch=getchar();
while(ch>='0'&&ch<='9')w=w*10+ch-'0',ch=getchar();
return q?-w:w;
}
int tot,cnt,S[MAXM],T[MAXM];
struct Dijskra{
static const int N=1010,M=(N*10)<<1;
int n,t,l;int d[N],fr[N];int to[M],ne[M],be[M],W[M];bool u[N];
struct node{
int s,p;
bool operator<(node a)const{return s>a.s;}
};
priority_queue<node>q;
IN void link(RG int u,RG int v,RG int w){
//if(w>l)return; this some edges didn't get
to[++t]=v;ne[t]=fr[u];fr[u]=t;W[t]=w;be[t]=u;
}
int Dij(int begin,int end){
for(int i=0;i<n;i++)d[i]=INF;
q.push((node){d[begin]=0,begin});memset(u,0,sizeof(u));
while(!q.empty()){
while(u[q.top().p]&&!q.empty())q.pop();
if(q.empty())break;
int x=q.top().p;q.pop();u[x]=1;
if(x==end||d[x]>l)break;
for(int o=fr[x],y;y=to[o],o;o=ne[o])
if(d[x]+W[o]<d[y]&&d[x]+W[o]<=l){
d[y]=d[x]+W[o];
q.push((node){d[y],y});
}
}
return d[end];
}
void pri(int end){
printf("YES\n");
for(int i=1;i<t-1;i+=2)
printf("%d %d %d\n",be[i],to[i],W[i]);
printf("%d %d %d\n",be[t-1],to[t-1],l-d[end]+W[t-1]);//this W[t-1]
for(int i=tot;i<=cnt;i++)printf("%d %d %d\n",S[i],T[i],(int)INF);exit(0);
}
}e;
int main()
{
freopen("D.in","r",stdin);
freopen("D.out","w",stdout);
int n=gi(),m=gi(),l=gi(),s=gi(),t=gi();e.l=l;e.n=n;
for(int i=1;i<=m;i++){
int u=gi(),v=gi(),w=gi();
if(w)e.link(u,v,w),e.link(v,u,w);
else S[++cnt]=u,T[cnt]=v;
}tot=1;//this
if(e.Dij(s,t)<l){printf("NO");return 0;}
if(e.d[t]==l)e.pri(t);
for(;tot<=cnt;tot++){
e.link(S[tot],T[tot],1);e.link(T[tot],S[tot],1);
if(e.Dij(s,t)<=l)break;
}tot++;
if(tot>cnt+1)return 0*puts("NO");
e.pri(t);
return 0;
}