• ZOJ-3946 Highway Project (最短路)


    题目大意:一张带权无向图,权有两个参数(d,c),分别表示走过这条边的时间和建造这条边的代价。要求选出一些边,使得0节点到其他点的距离之和最短,并在最短的基础上求最小代价。

    题目分析:这是16年浙江省赛的一道题。先求出0到所有点的最短路,然后找出所有可能在最短路径上的边,最后在每一个节点的入边之中都选一条具有最小代价的边。多么简单的一道题!!!

    代码如下:

    # include<iostream>
    # include<cstdio>
    # include<cstring>
    # include<vector>
    # include<queue>
    # include<list>
    # include<set>
    # include<map>
    # include<string>
    # include<cmath>
    # include<cstdlib>
    # include<algorithm>
    using namespace std;
    # define LL long long
    
    const int N=1005;
    const int INF=1000000000;
    const LL oo=1000000000000005;
    
    struct Edge
    {
    	int to,nxt;
    	LL c,d;
    };
    
    int n,m,cnt;
    Edge e[N*200];
    LL d[N*100];
    int head[N*100];
    vector<int>pre[N*100];
    
    void add(int u,int v,LL d,LL c)
    {
    	e[cnt].to=v;
    	e[cnt].d=d;
    	e[cnt].c=c;
    	e[cnt].nxt=head[u];
    	head[u]=cnt++;
    }
    
    void solve()
    {
    	for(int i=0;i<n;++i)
    		pre[i].clear();
    	
    	fill(d,d+n,oo);
    	d[0]=0;
    	queue<int>q;
    	q.push(0);
    	while(!q.empty())
    	{
    		int u=q.front();
    		q.pop();
    		for(int i=head[u];i!=-1;i=e[i].nxt){
    			int v=e[i].to;
    			if(d[v]>d[u]+e[i].d){
    				d[v]=d[u]+e[i].d;
    				q.push(v);
    			}
    		}
    	}
    	
    	q.push(0);
    	while(!q.empty()){
    		int u=q.front();
    		q.pop();
    		for(int i=head[u];i!=-1;i=e[i].nxt){
    			int v=e[i].to;
    			if(d[v]==d[u]+e[i].d){
    				pre[v].push_back(i);
    				q.push(v);
    			}
    		}
    	}
    	
    	LL ans1=0,ans2=0;
    	for(int i=0;i<n;++i){
    		ans1+=d[i];
    		LL minn=oo;
    		for(int j=0;j<pre[i].size();++j)
    			minn=min(minn,e[pre[i][j]].c);
    		if(minn==oo) continue;
    		ans2+=minn;
    	}
    	printf("%lld %lld
    ",ans1,ans2);
    }
    
    int main()
    {
    	int T;
    	scanf("%d",&T);
    	while(T--)
    	{
    		scanf("%d%d",&n,&m);
    		cnt=0;
    		memset(head,-1,sizeof(head));
    		int a,b;
    		LL c,d;
    		for(int i=0;i<m;++i){
    			scanf("%d%d%lld%lld",&a,&b,&d,&c);
    			add(a,b,d,c);
    			add(b,a,d,c);
    		}
    		solve();
    	}
    	return 0;
    }
    

      

  • 相关阅读:
    设计模式学习08:享元模式
    设计模式学习07:适配器模式
    设计模式学习06:策略模式和简单工厂模式
    XCode Debugger中的Icon符号的意义
    蒲公英——APP内测分发平台
    分享申请IDP账号的过程,包含duns申请的分享
    Dash——程序员的的好帮手:API文档浏览器+代码片段管理工具
    xScope——界面设计师的终极工具箱
    Alcatraz——Xcode插件管理工具
    苹果向开发者发布 Xcode 6.3.2 GM版 修复 Bug
  • 原文地址:https://www.cnblogs.com/20143605--pcx/p/5426398.html
Copyright © 2020-2023  润新知