zoukankan      html  css  js  c++  java
  • UVA11090 二分逼近+bf

    Going in Cycle!!

    You are given a weighted directed graph with n vertices and m edges. Each cycle in the graph has a weight, which equals to sum of its edges. There are so many cycles in the graph with different weights. In this problem we want to find a cycle with the minimum mean.

    Input

    The first line of input gives the number of cases, N. N test cases follow. Each one starts with two numbers n and m. m lines follow, each has three positive number a, b, c which means there is an edge from vertex a to b with weight of c.

    Output

    For each test case output one line containing Case #x: followed by a number that is the lowest mean cycle in graph with 2 digits after decimal place, if there is a cycle. Otherwise print No cycle found..

    Constraints

      • n ≤ 50

      • a, b ≤ n

      • c ≤ 10000000

    Sample Input

    2

    2 1

    1 2 1

    2 2

    1 2 2

    2 1 3

    Sample Output

    Case #1: No cycle found.

    Case #2: 2.5

    题意:n个点m条边的有向图,要求平均权值最小的回环

    假设最小回环的平均权值是tmp,这样,此图所有权边-tmp构造一个新图,此新图存在一个负环,很容易就得出,此负环就是我们需要的那个平均权值最小的回环。平均权值可以通过二分法得到

    下面的代码我以前写过,晚上写了一下,还没有在vj上试过 果然还是挂了哈,排除新图没有负环用了sum_weiths,数太大就超int了,其实应该用max_weight+1就可以了 :smile:

    #include <iostream>
    #include <cstdio>
    #include <cstdlib>
    #include <cstring>
    #include <cmath>
    #include <stack>
    #include <string>
    #include <queue>
    #include <vector>
    #include <algorithm>
    #include <ctime>
    using namespace std;
    
    //#define EdsonLin
    
    #ifdef EdsonLin
    #define debug(...) fprintf(stderr,__VA_ARGS__)
    #else
    #define debug(...)
    #endif // EdsonLin
    
    typedef long long ll;
    typedef double db;
    const ll inf = (1ll)<<60;
    const int MAXN = 50;
    const int MAXNN = 3e3+10;
    const ll MOD = 1000000007;
    const db eps = 1e-3;
    
    ll qp(ll a,ll b){ll ans=1;while(b){if(b&1)ans=ans*a%MOD;a=a*a%MOD;b>>=1;}return ans;}
    
    int n,m;
    int first[MAXN];
    int top;
    struct edge{
        int st;
        int to;
        double dist;
        int next;
    }e[MAXNN];
    double d[MAXN];
    int inq[MAXN];
    int cnt[MAXN];
    
    void init(){
        top = 0;
        memset(first,-1,sizeof(first));
    }
    
    void addedge(int u,int v,int dist){
        e[top].st = u;
        e[top].to = v;
        e[top].next = first[u];
        e[top].dist = dist;
        first[u] = top++;
    }
    
    bool bf(){
        //memset(d,0,sizeof(d));
        //memset(inq,0,sizeof(inq));
    
        queue<int>Q;
       // cout<<n<<endl;
        for(int i=0;i<n;i++){
            Q.push(i);
            d[i] = inq[i] = cnt[i] = 0;
        }
        inq[0] = 1;
        int u;
        while(!Q.empty()){
            u = Q.front();
            Q.pop();
            inq[u] = 0;
            for(int i=first[u];i!=-1;i=e[i].next){
                int v = e[i].to;
                if(d[v]>d[u]+e[i].dist){
                    d[v]=d[u]+e[i].dist;
                    if(!inq[v]){
                        Q.push(v);
                        inq[v] = 1;
                        cnt[v]++;
                        #ifdef EdsonLin
                            debug("Edson:%d
    ",v);
                        #endif // EdsonLin
                        if(cnt[v]>n)return true;
                    }
                }
            }
        }
        return false;
    }
    
    bool solve(double d){
        bool sg;
        #ifdef EdsonLin
            debug("Edson:%lf
    ",d);
        #endif // EdsonLin
        for(int i=0;i<top;i++)
            e[i].dist -= d;
        sg = bf();
        //cout<<"endl"<<endl;
        for(int i=0;i<top;i++)
            e[i].dist += d;
        return sg;
    }
    
    int main(){
        #ifdef EdsonLin
        //freopen("1.in","r",stdin);
        //freopen("1.out","w",stdout);
        int _time_jc = clock();
        #endif // EdsonLin
        int T;
        int mc=0;
        double mmax;
        scanf("%d",&T);
        while(T--){
            init();
            mmax = 0;
            scanf("%d%d",&n,&m);
            for(int i=0;i<m;i++){
                int a,b,c;
                scanf("%d%d%d",&a,&b,&c);
                a--;b--;
                addedge(a,b,c);
                mmax = max(mmax,c*1.0);
            }
            #ifdef EdsonLin
               // debug("Edosn:%lf
    ",tmp);
            #endif // Edson
    
            bool sg = solve(mmax+1);
            if(!sg){
                printf("Case #%d: No cycle found.
    ",++mc);
                continue;
            }
            double _e = mmax,_s = 0,_m;
            while(_e-_s>eps){
                _m = (_e+_s)/2;
                if(solve(_m)){
                    _e = _m;
                }else{
                    _s = _m;
                }
            }
            printf("Case #%d: %.2lf
    ",++mc,_s);
        }
    
    
        #ifdef EdsonLin
            debug("time: %d
    ",int(clock()-_time_jc));
        #endif // EdsonLin
    
        return 0;
    }
    View Code
    在一个谎言的国度,沉默就是英雄
  • 相关阅读:
    jxl导出excel的问题
    java.lang.IllegalStateException: getOutputStream() has already been called for this response解决方案
    在MyEclipse中用debug调试应用程序
    添加 MyEclipse Persistence Tools 类库
    使用递归算法结合数据库解析成java树形结构
    String.format()用法
    在ubuntu下使用Eclipse搭建Hadoop开发环境
    Ubuntu下伪分布式模式Hadoop的安装及配置
    ubuntu10.10手工安装jdk1.6
    docker 清理容器和镜像
  • 原文地址:https://www.cnblogs.com/EdsonLin/p/5521379.html
Copyright © 2011-2022 走看看