明显是dmxi-dmni
由于存在环,取路径最小值不能保证当前最小就是最终最小,所以不能用dij,有后效性也不能用dp
只能用spfa,无特殊数据是个线性算法。显然这题没卡。。
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define ls (o<<1)
#define rs (o<<1|1)
#define pb push_back
const double PI= acos(-1.0);
const int M = 1e6+7;
const int N= 1e5+7;
int head[2][M],cnt;
void init(){cnt=0,memset(head,0,sizeof(head));}
struct EDGE{int to,nxt,val;}ee[2][M];
void add(int x,int y,int z){ee[z][++cnt].nxt=head[z][x],ee[z][cnt].to=y,head[z][x]=cnt;}
int a[N],n,m;
int d[2][M];
int vs[M];
void spfa()
{
memset(d[0],0x3f,sizeof(d[0]));
memset(vs,0,sizeof(vs));
queue<int>q;
q.push(1);d[0][1]=a[1],vs[1]=1;
while(q.size())
{
int u=q.front();q.pop();vs[u]=0;
for(int i=head[0][u];i;i=ee[0][i].nxt)
{
int v=ee[0][i].to;
int ans=min(d[0][u],a[v]);
if(d[0][v]>ans)
{
d[0][v]=ans;
if(!vs[v])q.push(v),vs[v]=1;
}
}
}
memset(d[1],0,sizeof(d[1]));
memset(vs,0,sizeof(vs));
d[1][n]=a[n],vs[n]=1;q.push(n);
while(q.size())
{
int u=q.front();q.pop();vs[u]=0;
for(int i=head[1][u];i;i=ee[1][i].nxt)
{
int v=ee[1][i].to;
int ans=max(d[1][u],a[v]);
if(d[1][v]<ans)
{
d[1][v]=ans;
if(!vs[v])q.push(v),vs[v]=1;
}
}
}
}
int main()
{
scanf("%d%d",&n,&m);
for(int i=1;i<=n;i++)
scanf("%d",&a[i]);
for(int i=1;i<=m;i++)
{
int u,v,op;
scanf("%d%d%d",&u,&v,&op);
add(u,v,0),add(v,u,1);
if(op==2)add(v,u,0),add(u,v,1);
}
spfa();
int ans=0;
for(int i=1;i<=n;i++)
{
ans=max(ans,d[1][i]-d[0][i]);
// cout<<i<<" "<<d[0][i]<<" "<<d[1][i]<<endl;
}
printf("%d\n",ans);
return 0;
}