2017年华东师范大学网络赛 G

来源:互联网 发布:网格交易软件 编辑:程序博客网 时间:2024/04/30 05:38

G. 铁路修复计划
Time limit per test: 2.0 seconds
Time limit all tests: 15.0 seconds
Memory limit: 256 megabytes
Accept / Submit: 146 / 1219

在 A 国有很多城际铁路。这些铁路都连接两个城市(城市从 1 到 n 编号),可以双向通行,使得任意两个城市之间都由铁路网联系起来。

不过在一次星球大战之后,所有的铁路都经历了不同程度的损伤以至于无法通行了。由于经费紧缺,A 国政府不愿意再出资造新的铁路。对于原有的城际铁路,根据铁路的实际情况,有以下两种处理办法:

使用国内技术进行修复:主要针对损坏情况不是很严重的铁路。国内公司会对铁路状况进行评估,然后如实开出铁路修复的费用。
使用国外技术进行修复:主要针对损坏情况严重的铁路。国外公司也会对铁路情况进行评估,然后按照铁路实际修复费用的 k 倍来收费(其中 k 是一个由国外公司决定的实数,不管怎么说,优惠是不可能的,所以 k≥1)。
A国政府修复铁路的总预算是 M,目标是要让任意两个城市之间都能通过铁路联系起来。在预算不够且能够完成目标的条件下,显然没必要修复每一条铁路。

国外公司通过不知什么途径了解到了 A 国政府的总预算 M,他们现在要把 k 定下来,并且希望 k 尽可能得大。但 k 又不能太大,不然,如果 A 国政府发现无法完成任务的话,整个订单都会泡汤。

Input
测试数据包含不超过 30 个测试文件。每个测试文件是单个测试点。

第一行是三个整数 n,m,M (2≤n≤105,n−1≤m≤min{105,n(n−1)2},1≤M≤1015)。

接下来 m 行,每行四个整数 ui,vi,ti,fi。表示一条城际铁路,连接着 ui 和 vi 城市,ti 表示铁路实际修复费用。fi=1 表示只能由国外公司修复,fi=0 表示由国内公司修复。(1≤ui,vi≤n,ui≠vi,1≤ti≤106,fi∈{0,1})。输入保证两个城市之间不会存在多条铁路。

输入保证:

在国外公司不乱收费 (k=1) 的情况下,使用预算能完成要求。
完全不使用国外技术,只使用国内技术,是不能完成目标的。
Output
求 k 的最大值。输出答案与标准答案相差不超过 10−6 即判为正确。

Examples
input
3 3 9
1 2 1 1
1 3 2 0
2 3 1 1
output
7.000000
input
3 3 9
1 2 1 1
1 3 2 1
2 3 2 1
output
3.000000

题解: 二分答案 , 然后用Kruskal写判断就行了, 二分是写相等有三组数据错 , 加一减一却过了 ,这道题我错了N次。。

#include <bits/stdc++.h>#define sc scanf#define pr printfusing namespace std;const int N = 110000;struct Note{    int u , v , f;    double cost , cost1;}note[N];int n , m ,  fa[N]; double fin_cost;inline void init(double k);bool kruskal(double k);double binary_search_ans(double l , double r);int find_fa(int x);void union_xy(int x , int y);bool cmp(Note &a , Note &b){    //return b.cost- a.cost > 1e-9; //用这个就超时 , 无奈,在比赛的时候我是没想到一直TLE的原因就是这...    return a.cost < b.cost;}int main(){    memset(note,0,sizeof(note));    int i , j , u , v , t , f;    sc("%d %d %lf",&n, &m , &fin_cost);    for(i=1; i<=m; i++)        sc("%d %d %lf %d",&note[i].u , &note[i].v , &note[i].cost1 , &note[i].f);    pr("%06f\n",binary_search_ans(1 , 1e10));//范围纠结了很久    return 0;}int find_fa(int x){    if(fa[x] == x) return x;    return fa[x] = find_fa(fa[x]);}void union_xy(int x , int y){    int ax = find_fa(x);    int ay = find_fa(y);    if(ax != ay)        fa[ax] = ay;}inline void init(double k){    for(int i=1; i<=n; i++) fa[i] = i;    for(int i=1; i<=m; i++)    {        if(note[i].f)            note[i].cost = note[i].cost1*k;        else            note[i].cost = note[i].cost1;    }    sort(note+1 , note+1+m , cmp);}bool kruskal(double k){    double sum = 0;    init(k);    for(int i=1; i<=m; i++)    {        int u = note[i].u;        int v = note[i].v;        if(find_fa(u) != find_fa(v))        {            sum += note[i].cost;            union_xy(u,v);        }    }    if(fin_cost - sum > 1e-9 )return 1;    return 0;}double binary_search_ans(double l , double r){    double ans , mid;    for(int i=0; i<100; i++)    {        mid = (l+r)/2;        if(!kruskal(mid))            r = mid - 1;        else            l = mid + 1, ans = mid;    }    return ans;}
0 0
原创粉丝点击