• 洛谷P1342请柬


    传送门啦

    核心思想:两遍最短路.

    1号点去各地的时间直接套最短路模板,各地到1号点时间用逆向思维,视为求1号点沿反边到各地的时间即可.

    #include <iostream>
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    #include <queue>
    #define re register
    using namespace std;
    const int maxn = 1000005;
    
    inline int read(){
    	char ch = getchar();
    	int f = 1 , x = 0;
    	while(ch > '9' || ch < '0'){if(ch == '-')f = -1;ch = getchar();}
    	while(ch >= '0' && ch <= '9'){x = (x << 1) + (x << 3) + ch - '0';ch = getchar();}
    	return x * f;
    }
    
    int n,m,u,v;
    long long w;
    int head1[maxn],tot1,head2[maxn],tot2;
    long long ans,dis1[maxn],dis2[maxn];
    
    struct Edge{
    	int from,to,next;
    	long long val;
    }edge1[maxn<<1] , edge2[maxn<<1];
    
    struct Node{
    	int u,d;
    	bool operator < (const Node &f) const {
    		return d > f.d;
    	}
    };
    
    inline void add1(int u,int v,long long w){
    	edge1[++tot1].from = u;
    	edge1[tot1].to = v;
    	edge1[tot1].val = w;
    	edge1[tot1].next = head1[u];
    	head1[u] = tot1;
    }
    
    inline void add2(int u,int v,long long w){
    	edge2[++tot2].from = u;
    	edge2[tot2].to = v;
    	edge2[tot2].val = w;
    	edge2[tot2].next = head2[u];
    	head2[u] = tot2;
    }
    
    inline void dijk1(int s){
    	for(re int i=1;i<=n;i++)  dis1[i] = 1e9;
    	priority_queue<Node> q;
    	dis1[s] = 0;
    	q.push((Node) {s , dis1[s]});
    	while(!q.empty()){
    		Node cur = q.top();
    		q.pop();
    		int d = cur.d , u = cur.u;
    		if(d != dis1[u]) continue;
    		for(re int i=head1[u];i;i=edge1[i].next){
    			int v = edge1[i].to;
    			if(dis1[v] > dis1[u] + edge1[i].val){
    				dis1[v] = dis1[u] + edge1[i].val;
    				q.push((Node) {v , dis1[v]});
    			}
    		}
    	}
    }
    
    inline void dijk2(int s){
    	for(re int i=1;i<=n;i++)  dis2[i] = 1e9;
    	priority_queue<Node> q;
    	dis2[s] = 0;
    	q.push((Node) {s , dis2[s]});
    	while(!q.empty()){
    		Node cur = q.top();
    		q.pop();
    		int d = cur.d , u = cur.u;
    		if(d != dis2[u]) continue;
    		for(re int i=head2[u];i;i=edge2[i].next){
    			int v = edge2[i].to;
    			if(dis2[v] > dis2[u] + edge2[i].val){
    				dis2[v] = dis2[u] + edge2[i].val;
    				q.push((Node) {v , dis2[v]});
    			}
    		}
    	}
    }
    
    int main(){
    	n = read(); m = read();
    	for(int i=1;i<=m;i++){
    		u = read(); v = read(); scanf("%lld",&w);
    		add1(u , v , w);
    		add2(v , u , w);
    	}
    	dijk1(1);
    	for(int i=2;i<=n;i++)
    		ans += dis1[i];
    	dijk2(1);	
    	for(int i=n;i>=2;i--){	
    		ans += dis2[i];
    	}
    	printf("%lld
    ",ans);
    	return 0;
    }
    
    顺风不浪,逆风不怂。
  • 相关阅读:
    url末尾的斜杠作用
    awk 工具可以很灵活地对文本进行处理,这里的 awk '{print $2}'是指第二列的内容,是运行的程序 ID。 杀死指定进程
    nil和空切片
    WaitGroup源码设计,
    2
    t
    Go内置的定时器
    分布式定时器
    1 2 交换
    order by 1 DESC 2 desc
  • 原文地址:https://www.cnblogs.com/Stephen-F/p/9908897.html
Copyright © 2020-2023  润新知