BZOJ 1003 最短路+DP
看数据范围特别小,然后就暴力dp就好了~
还要想清楚,选择的路径,一定是某一天的最短路!
View Code
1 #include <iostream> 2 #include <cstring> 3 #include <cstdio> 4 #include <cstdlib> 5 #include <algorithm> 6 7 #define N 200 8 #define M 100000 9 10 using namespace std; 11 12 int head[N],next[M],to[M],len[M]; 13 int can[N][N],pt[M],st[M],ed[M]; 14 int dis[N],q[M],dp[N]; 15 bool vis[N],bh[N]; 16 int n,m,K,e,d,cnt; 17 18 inline void add(int u,int v,int w) 19 { 20 to[cnt]=v; len[cnt]=w; next[cnt]=head[u]; head[u]=cnt++; 21 } 22 23 inline void read() 24 { 25 memset(head,-1,sizeof head); cnt=0; 26 scanf("%d%d%d%d",&n,&m,&K,&e); 27 for(int i=1,a,b,c;i<=e;i++) 28 { 29 scanf("%d%d%d",&a,&b,&c); 30 add(a,b,c); add(b,a,c); 31 } 32 scanf("%d",&d); 33 for(int i=1;i<=d;i++) scanf("%d%d%d",&pt[i],&st[i],&ed[i]); 34 } 35 36 inline void build(int l,int r) 37 { 38 memset(bh,true,sizeof bh); 39 for(int i=1;i<=d;i++) 40 { 41 if(st[i]>r||ed[i]<l) continue; 42 bh[pt[i]]=false; 43 } 44 } 45 46 inline int spfa() 47 { 48 memset(dis,0x3f,sizeof dis); 49 int h=1,t=2,sta; 50 q[1]=1; vis[1]=true; dis[1]=0; 51 while(h<t) 52 { 53 sta=q[h++]; vis[sta]=false; 54 for(int i=head[sta];~i;i=next[i]) 55 if(bh[to[i]]&&dis[to[i]]>dis[sta]+len[i]) 56 { 57 dis[to[i]]=dis[sta]+len[i]; 58 if(!vis[to[i]]) vis[to[i]]=true,q[t++]=to[i]; 59 } 60 } 61 return dis[m]; 62 } 63 64 inline void go() 65 { 66 for(int i=1;i<=n;i++) 67 for(int j=i;j<=n;j++) 68 { 69 build(i,j); 70 can[i][j]=spfa(); 71 } 72 memset(dp,0x3f,sizeof dp); 73 dp[0]=0; 74 for(int i=1;i<=n;i++) 75 for(int j=1;j<=i;j++) 76 { 77 if(can[j][i]>=0x3f3f3f3f||dp[j-1]>=0x3f3f3f3f) continue; 78 dp[i]=min(dp[i],dp[j-1]+can[j][i]*(i-j+1)+K); 79 } 80 printf("%d\n",dp[n]-K); 81 } 82 83 int main() 84 { 85 read(); 86 go(); 87 return 0; 88 }
没有人能阻止我前进的步伐,除了我自己!