poj1062——昂贵的聘礼

本文介绍了一种结合枚举和Dijkstra算法解决特定路径寻找问题的方法。通过枚举节点等级范围并应用Dijkstra算法来计算最短路径,解决了带有条件限制的最短路径问题。代码实现了基于输入数据构建图,并通过枚举不同的节点等级范围来找到最优解。

枚举+dij(最短路算法)。

ps:很多题目在没有思路的情况下,可以搜索,或者枚举。

#include<iostream> #include<string> #include<cstdio> using namespace std; #define N 105 #define maxcost 1e8 int dist[N],vis[N],d[N],rank[N]; class node { public: int to,dis,next; }; node g[15000]; int head[N],cnt; int n,m; void add(int v,int to,int dis) { g[++cnt].to =to; g[cnt].dis =dis; g[cnt].next=head[v]; head[v]=cnt; } int solve(int low,int high) { int i,j,k,v; int dis,min; for(i=1;i<=n;i++) dist[i]=maxcost; dist[1]=d[1]; for(i=head[1];i;i=g[i].next ) { int v=g[i].to ; if(rank[v]<=high&&rank[v]>=low) { if(dist[v]>g[i].dis +d[v]) { dist[v]=g[i].dis +d[v]; } } } memset(vis,true,sizeof(vis)); vis[1]=false; for(i=1;i<=n;i++) { min=maxcost;k=i; for(j=1;j<=n;j++) { if(vis[j]&&dist[j]<min&&rank[j]<=high&&rank[j]>=low) { min=dist[j]; k=j; } } if(min==maxcost) break; vis[k]=false; for(j=head[k];j;j=g[j].next ) { v=g[j].to ; if(rank[v]>=low&&rank[v]<=high) { if(dist[v]>dist[k]-d[k]+g[j].dis +d[v]) { dist[v]=dist[k]-d[k]+g[j].dis+d[v] ; } } } } min=d[1]; for(i=2;i<=n;i++) if(min>dist[i]) min=dist[i]; return min; } int main() { cnt=0; int i,j,p,l,x,v,dis,rankroot; cin>>m>>n; for(i=1;i<=n;i++) { cin>>p>>l>>x; if(i==1) rankroot=l; rank[i]=l; d[i]=p; for(j=0;j<x;j++) { cin>>v>>dis; add(i,v,dis); } } int ans=maxcost,min; for(i=0;i<=m;i++) { if(rankroot-m+i>=0) { min=solve(rankroot-m+i,rankroot+i); ans=min<ans?min:ans; } } cout<<ans<<endl; return 0; }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值