poj1062昂贵的聘礼

要先分段枚举,在分别进行一次Dijkstra。例如M=2,酋长等级为3,则要分别枚举1~3、2~4、3~5。

#include<iostream>
#include<stdio.h>
#include<string.h>
#include<queue>
#include<vector>
#define INF 0x3f3f3f3f
#define MAXD 110
using namespace std;
int N,M,graph[MAXD][MAXD],P,L,X,T,V,limit[MAXD],value[MAXD];

int min(int a,int b)
{
    if(a<b)
    return a;
    else
    return b;
}

struct NODE
{
int d;
int L;
} node[MAXD];

class cmp
{
    public:
    bool operator()(int x,int y)
    {
        return node[x].d > node[y].d;
    }
};

void relax(int u,int v)
{
    if(node[v].d>node[u].d+graph[u][v])
    node[v].d=node[u].d+graph[u][v];
}
void DIJKSTRA()
{
    priority_queue<int ,vector<int>,cmp > que;
    int i;
    for(i=1;i<=N;i++)
    node[i].d=value[i];
    for(i=1;i<=N;i++)
    {
        if(limit[i])
        que.push(i);
    }
    int cur,next;
    while(!que.empty())
    {
        cur=que.top();
        que.pop();
        for(i=1;i<=N;i++)
        {
            next=i;
            relax(cur,next);
        }
    }
}
int main()
{
    //freopen("test.txt","r",stdin);
    scanf("%d%d",&M,&N);
    int i,j;
    memset(graph,0x3f,sizeof(graph));
    for(i=1;i<=N;i++)
    {
        scanf("%d%d%d",&P,&L,&X);
        value[i]=P;
        node[i].L=L;
        for(j=1;j<=X;j++)
        {
            scanf("%d%d",&T,&V);
            graph[T][i]=V;
        }
    }
    int result=INF;
    for(i=0;i<=M;i++)
    {
        memset(limit,0,sizeof(limit));
        for(j=1;j<=N;j++)
        {
            if(node[j].L>=node[1].L-M+i&&node[j].L<=node[1].L+i)
            limit[j]=1;
        }
        DIJKSTRA();
        result=min(result,node[1].d);
    }
    printf("%d\n",result);
}
原文地址:https://www.cnblogs.com/longlongagocsu/p/2824795.html