ccpc20190823

04

http://acm.hdu.edu.cn/showproblem.php?pid=6705

Analysis; each edge of the form into the first stack, the stack by the path weight in ascending order, and then takes out the top of the stack, with the sides extended v new path. However, the points may be of a very large (e.g., FIG chrysanthemum), can be found, then the edge of the sorting,

Each need to extend only a minimum current point side, and extended to the lower edge of one side to the current point. Stack needs to record the current node, the current distance, the distance from a node, the current node is extended to be spread nowadays one side.

(Note that if the same current-time extended even point out the value of the ownership side, will the TLE, is in fact not necessary.)
Complexity: O (k * log (m + k))

#include<queue>
#include<vector>
#include<algorithm>
#include<cstdio>
#include<cstring>
using namespace std;
typedef long long ll;
#define pb push_back
const int M=1e5+5;
struct node{
    ll cost;
    int u,id;
    node(ll costt=0,int uu=0,int idd=0 ){
        cost=costt;
        u=uu;
        id=idd;
    }
    bool operator < ( const node &b)const{
        return cost>b.cost;
    }
};
#define pli pair<ll,int>
vector<pli> e[M];
ll ans[M];
int a[M];
priority_queue<node> que;
int main(){
    int t;
    scanf("%d",&t);
    while(t--){
        int n,m,q;
        scanf("%d%d%d",&n,&m,&q);
        for(int i=0;i<=n;i++)
            e[i].clear();
        while(!que.empty())
            que.pop();
        for(int i=1;i<=m;i++){
            int u,v;
            ll w;
            scanf("%d%d%lld",&u,&v,&w);
            e[u].pb(pli(w,v));
        }
        int maxxk=0;
        for(int i=1;i<=q;i++){
            scanf("%d",&a[i]);
            maxxk=max(maxxk,a[i]);
        }
        for(int i=1;i<=n;i++)
            sort(e[i].begin(),e[i].end());
        for(int i=1;i<=n;i++)
            if(e[i].size())
                que.push(node(e[i][0].first,i,0));
        int tot=0;
        while(!que.empty()){
            node now=que.top();
            que.pop();
            int u=now.u;
            int id=now.id;
            ll Cost=now.cost;
            if(Cost)
                ans[++tot]=Cost;
            if(tot==maxxk)
                break;
            if(id<(int)e[u].size()-1)
                que.push(node(Cost-e[u][id].first+e[u][id+1].first,u,id+1));
            int v=e[u][id].second;
            if(e[v].size())
                que.push(node(Cost+e[v][0].first,v,0));
        }
        for(int i=1;i<=q;i++)
            printf("%lld\n",ans[a[i]]);
    }
    return 0;
}
View Code

 

Guess you like

Origin www.cnblogs.com/starve/p/11403256.html