蒟蒻求助

P1462 通往奥格瑞玛的道路

白猫_琉璃 @ 2019-06-02 20:32:40

RT

评测记录

代码

#include<iostream>
#include<cstdio>
#include<climits>
#include<queue>
using namespace std;

const int MAXN = 10005,MAXM = 100010,INF = INT_MAX;
int n,m,b,x,y,z,head[MAXN],cnt,crtm,mny[MAXN],dis[MAXN],le = INF,ri,mid,id,d,beu;
bool vis[MAXN],yes;

struct Edge {
    int to;
    int w;
    int nxt;
} l[MAXM];
struct Node {
    int id;
    int dis;
};

priority_queue<Node> q;
bool operator < (const Node &a,const Node &b){
    return (a.dis > b.dis);
}

void add(int x,int y,int z){
    cnt++;
    l[cnt].to = y;
    l[cnt].w = z;
    l[cnt].nxt = head[x];
    head[x] = cnt;
}
void init(){
    for(int i=1;i<=n;i++){
        dis[i] = INF;
        vis[i] = false;
    }
}
bool dijk(){
    init();
    dis[1] = 0;
    q.push(Node{1,0});
    Node crt;
    while(!q.empty()){
        crt = q.top();
        q.pop();
        id = crt.id;
        if(vis[id]){
            continue;
        }
        //如果当前城市的收费大于要求的收费那就不走 
        if(mny[id] > mid){
            continue;
        }
        vis[id] = true;
        d = dis[id] = crt.dis;
        for(int i=head[id];i;i=l[i].nxt){
            beu = l[i].to;
            if(!vis[beu] && dis[beu] > d + l[i].w){
                q.push(Node{beu,d + l[i].w});
            }
        }
    }
    if(dis[n] < b){
        yes = true;
        return true;
    }else{
        return false;
    }
}

int main(void){
    //得到点的数量、边的数量和歪嘴哦的血量
    scanf("%d%d%d",&n,&m,&b);
    for(int i=1;i<=n;i++){
        scanf("%d",&crtm);
        mny[i] = crtm;
        ri = max(crtm,ri);
        le = min(crtm,le);
    }
    for(int i=1;i<=m;i++){
        scanf("%d%d%d",&x,&y,&z);
        add(x,y,z);
        add(y,x,z); 
    } 
    while(le < ri){
        mid = (le + ri) / 2;
        if(dijk()){
            ri = mid;
        }else{
            le = mid + 1;
        }
    }
    mid = le;
    dijk();
    if(yes){
        printf("%d",le);
    }else{
        printf("AFK");
    }
    return 0;
}

|