自己在本地用c++14明明样例都过了阿...
求大佬hack啊QAQ!!!
思路是用Floyed计算两个点之间需要转接的最小次数(way)
随后用dp求最大值
(不知道哪里错了(ノД`)・゜・。 如果这道0pts了提高就只有65惹...)
#include<cmath>
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
int n,m,k,sc[2510],st,ed,way[2510][2510],s[2510],v[2510],f[2510][5],maxn,maxp,ans;
int main(){
// freopen("holiday.in","r",stdin);
// freopen("holiday.out","w",stdout);
scanf("%d%d%d",&n,&m,&k);
for(int i=2;i<=n;i++) scanf("%d",&sc[i]);
memset(way,127,sizeof(way));
for(int i=1;i<=m;i++){
scanf("%d%d",&st,&ed);
way[st][ed]=0;
way[ed][st]=0;
way[i][i]=-1;
}
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
for(int p=1;p<=n;p++){
way[p][j]=min(way[p][j],way[p][i]+way[i][j]+1);
}
}
}
// for(int i=1;i<=n;i++){
// printf("I:%d W:%d\n",i,way[1][i]);
// }
memset(f,128,sizeof(f));
f[1][0]=0;
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
for(int p=1;p<=4;p++){
if(i==j) continue;
if(way[i][j]<=k||way[j][i]<=k){
f[i][p]=max(f[i][p],f[j][p-1]+sc[i]);
}
}
}
maxn=-0x3f3f3f3f;
maxp=0;
for(int j=1;j<=4;j++){
if(f[i][j]>maxn){
maxn=f[i][j];
maxp=j;
}
}
// printf("I:%d MAXN:%d MAXP:%d\n",i,maxn,maxp);
}
for(int i=1;i<=n;i++){
if(way[1][i]<=k||way[i][1]<=k){
ans=max(ans,f[i][4]);
}
}
// printf("%d\n",way[1][189]);
printf("%d",ans);
return 0;
}