poj1062 昂贵的聘礼(dijkstra+枚举)

1、本来1作为起点,写着写着发现如果是将1作为源点,后续的改变会影响刚刚改变的值。所以应该额外置一个零点,将1置为终点,然后返回dis[1]
2、price[i]就是一开始的dis[i],这是因为可以不换东西直接用这个东西的本价值,如果可以通过替换,再对dis[i]进行更新。
3、注意dis[i]的更新要写在dijsktra里面,每次枚举都要重新赋值。
4、关于枚举:轮流取每一个点当做等级最低的点,那么比它大的点或者小它超过m的点都不能再遍历。这样就不会漏掉情况了。

#include<iostream>
#include<algorithm>
using namespace std;
#define maxn 100+5
int M,N;
int edge[maxn][maxn];
int price[maxn];
int grade[maxn];
int dis[maxn];
int vis[maxn];
int dijkstra()
{
 for(int i=1;i<=N;i++)
 {
  dis[i]=edge[0][i];
 }
 int minn=1e9;
 int index;
 for(int j=1;j<=N;j++)
 {
 minn=1e9;
 for(int i=1;i<=N;i++)
 {
  if(vis[i]==0&&minn>dis[i])
  {
   minn=dis[i];
   index=i;
  }
 }
 vis[index]=1;
 for(int i=1;i<=N;i++)
 {
  if(vis[i]==0&&dis[i]>dis[index]+edge[index][i])
   dis[i]=dis[index]+edge[index][i];
 }
 }
 return dis[1];
}
int main()
{
 while(cin>>M>>N)
 {//超过M不可以
 int t;
 int temp;
 for(int i=0;i<=N;i++)
 {
  for(int j=0;j<=N;j++)
  {
   edge[i][j]=1e9;
  }
 }
 for(int i=1;i<=N;i++)
 {
  cin>>price[i];
  cin>>grade[i];
  cin>>t;
  while(t--)
  {
   cin>>temp;
   cin>>edge[temp][i];//从temp到i,可用temp替代i
  }
  edge[0][i]=price[i];
 }
 int ans=1e9;
 for(int i=1;i<=N;i++)
 {
  for(int j=1;j<=N;j++)
  {
  if(grade[j]<grade[i]||grade[j]-grade[i]>M) vis[j]=1;
  else vis[j]=0;
  }
  ans=min(ans,dijkstra());
 }
 cout<<ans<<endl;
 }
}
发布了16 篇原创文章 · 获赞 1 · 访问量 267

猜你喜欢

转载自blog.csdn.net/weixin_44254608/article/details/104682287
今日推荐