标签:
Time Limit: 1000MS Memory Limit: 10000K
Description
Input
Output
Sample Input
1 4 10000 3 2 2 8000 3 5000 1000 2 1 4 200 3000 2 1 4 200 50 2 0
Sample Output
5250
题意:就是用其他的东西去交换得到第一个东西,使得花费最少。
分析:换东西有花费,很容易想到用最短路。将N个东西编号,可以交换就连一条边,边权为花费值,增加一个点,它到其他所有点的边权就是这个物品本身的花费。由于还有等级限制,因此一些边是不能加的,
我们可以枚举可行的等级:P[1]-m~P[1].然后每次考虑等级在这个之上的物品,每次求一次最短路,在取个min就好了。
#include<stdio.h> #include<string.h> #include<iostream> #include<algorithm> using namespace std; const int MAXN = 110; const int INF = 0x3f3f3f3f; struct Node{ int v,k,x; }a[MAXN]; int cost[MAXN][MAXN]; int dis[MAXN]; int val[MAXN]; bool vis[MAXN]; int t[MAXN][MAXN],v[MAXN][MAXN]; void Dijkstra(int n,int st) { for(int i=1;i<=n;i++){ dis[i]=INF; vis[i]=false; } dis[st]=0; for(int j=0;j<n;j++){ int Min=INF; int k=-1; for(int i=1;i<=n;i++){ if(!vis[i]&&Min>dis[i]){ Min=dis[i]; k=i; } } if(k==-1) break; vis[k]=true; for(int i=1;i<=n;i++) if(!vis[i]&&dis[k]+cost[k][i]<dis[i]) dis[i]=dis[k]+cost[k][i]; } } int main() { int m,n; int tol=1; scanf("%d%d",&m,&n); for(int i=1;i<=n;i++){ scanf("%d%d%d",&a[i].v,&a[i].k,&a[i].x); for(int j=1;j<=a[i].x;j++){ scanf("%d%d",&t[i][j],&v[i][j]); } } int ans=INF; tol=1; for(int k=max(0,a[1].k-m);k<=a[1].k;k++){ for(int i=1;i<=n+1;i++){ for(int j=1;j<=n+1;j++){ if(i==j) cost[i][j]=0; else cost[i][j]=INF; } } for(int i=1;i<=n;i++){ if(a[i].k>k+m||a[i].k<k) continue; cost[n+1][i]=a[i].v; for(int j=1;j<=a[i].x;j++){ if(a[t[i][j]].k>=k&&a[t[i][j]].k<=k+m) cost[t[i][j]][i]=v[i][j]; } } Dijkstra(n+1,n+1); ans=min(ans,dis[1]); } printf("%d\n",ans); return 0; }
标签:
原文地址:http://www.cnblogs.com/wangdongkai/p/5635671.html