//此题的关键在于等级限制的处理,最好的办法是采用枚举,即假设酋长等级为5,等级限制为2,那么需要枚举等级从3~5,4~6,5~7
//然后就是dij了,至于为什么要用dij,看个人喜好,毕竟这里等级处理要对vis数组进行标记
//处理了等级问题,就可以枚举等级数组,n倍dij跑完本题了,nlogn0ms搞定
//以下为具体代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<iostream>
using namespace std;
#define inf 0x3fffffff
int maze[110][110];
int dis[110],degree[110],val[110],vis[110];
int m,n;
void init()
{
memset(dis,inf,sizeof(dis));
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
maze[i][j]=inf;
}
int dij()
{
for(int i=1;i<=n;i++)
dis[i]=val[i];
for(int i=1;i<=n;i++)
{
int minn=inf,mark=inf;
for(int j=1;j<=n;j++)
{
if(!vis[j]&&dis[j]<minn)
{
minn=dis[j];
mark=j;
}
}
if(minn==inf)break;
vis[mark]=true;
for(int j=1;j<=n;j++)
{
if(!vis[j]&&dis[j]>dis[mark]+maze[mark][j])
{
dis[j]=dis[mark]+maze[mark][j];
}
}
}
return dis[1];
}
int main()
{
while(~scanf("%d%d",&m,&n))
{
init();
int x,a,b,tmp;
int ans=inf;
for(int i=1;i<=n;i++)
{
scanf("%d%d%d",&val[i],°ree[i],&x);
while(x--)
{
scanf("%d%d",&a,&b);
maze[a][i]=b;
}
}
for(int i=1;i<=n;i++)
{
for(int j=1;j<=n;j++)
{
if(degree[j]>=degree[i]&°ree[j]<=degree[i]+m)
{
vis[j]=false;
}
else
{
vis[j]=true;
}
}
tmp=dij();
ans=min(ans,tmp);
}
cout<<ans<<endl;
}
return 0;
}
poj 1602 昂贵的聘礼
最新推荐文章于 2023-03-06 18:29:25 发布