• UVA 11090 Going in Cycle!!


    要求给定的图的中平均权值最小的环,注意处理自环的情况就能过了。

    按照w1+w2+w3+….wn < n*ave的不等式,也就是(w1-ave) + (w2-ave) +…..(wn-ave) < 0,将每条边减去ave看是否存在负权回路,然后不断二分,由于保留两位小数,所以至少二分log(10^7)= 30次。

    代码:

    #include <iostream>
    #include <sstream>
    #include <cstdio>
    #include <climits>
    #include <cstring>
    #include <cstdlib>
    #include <string>
    #include <stack>
    #include <map>
    #include <cmath>
    #include <vector>
    #include <queue>
    #include <algorithm>
    #define  esp 1e-6
    #define  pi acos(-1.0)
    #define  pb push_back
    #define  lson l, m, rt<<1
    #define  rson m+1, r, rt<<1|1
    #define  mp(a, b) make_pair((a), (b))
    #define  in  freopen("in.txt", "r", stdin);
    #define  out freopen("out.txt", "w", stdout);
    #define  print(a) printf("%d
    ",(a));
    #define  bug puts("********))))))");
    #define  stop  system("pause");
    #define  Rep(i, c) for(__typeof(c.end()) i = c.begin(); i != c.end(); i++)
    #define  inf 0x0f0f0f0f
    
    using namespace std;
    typedef long long  LL;
    typedef vector<int> VI;
    typedef pair<int,int> pii;
    typedef vector<pii> VII;
    typedef vector<pii, int> VIII;
    typedef VI:: iterator IT;
    const int maxn = 100;
    
    struct Edge
    {
        int from, to;
        double dist;
    };
    
    struct Bellman_Ford
    {
        int n, m;
        vector<Edge> edges;
        VI G[maxn];
        double d[maxn];
        int p[maxn];
        int inq[maxn];
        int cnt[maxn];
    
        void init(int n)
        {
            this->n = n;
            for(int i = 0; i < n; i++)
            {
                G[i].clear();
            }
            edges.clear();
        }
    
        void add(int from, int to, double dist)
        {
            edges.pb((Edge)
            {
                from, to, dist
            });
            m = edges.size();
            G[from].pb(m-1);
        }
        bool negativeCircle(double L)
        {
            memset(cnt, 0, sizeof(cnt));
            memset(inq, 0, sizeof(inq));
            queue<int> q;
    
            for(int i = 0; i < n; i++)
            {
                d[i] = 0;
                inq[0] = 1;
                q.push(i);
            }
            while(!q.empty())
            {
                int u = q.front();
                q.pop();
                inq[u] = 0;
                for(int i = 0; i < G[u].size(); i++)
                {
                    Edge &e = edges[G[u][i]];
                    if(d[e.to] > d[u] + e.dist - L)
                    {
                        d[e.to] = d[u] + e.dist - L;
                        if(!inq[e.to])
                        {
                            q.push(e.to);
                            inq[e.to] = 1;
                        }
                        if(++cnt[e.to] > n)
                        {
                            return true;
                        }
                    }
                }
            }
            return false;
        }
    } solver;
    
    int main(void)
    {
    
        int T;
        for(int t = scanf("%d", &T); t <= T; t++)
        {
            printf("Case #%d: ", t);
            int n, m;
            scanf("%d%d", &n, &m);
            solver.init(n);
            double ans = inf + 100;
    
            double l = (double)inf*10, r = 0;
            while(m--)
            {
                int u, v;
                double w;
                scanf("%d%d%lf", &u, &v, &w);
                u--, v--;
                if(u == v)
                    ans = min(ans, w);
                solver.add(u, v, w);
                l = min(l, w);
                r = max(r, w);
            }
            int flag= 0;
            double mid = (l+r)/2;
            for(int i = 0; i < 30; i++)
            {
                if(solver.negativeCircle(mid))
                    flag = 1, r = mid-0.001;
                else l = mid+0.001;
                mid = (l+r)/2;
            }
            if(flag)
                printf("%.2f
    ", min(ans, mid));
                else if(ans < inf)
                    printf("%.2f
    ", ans);
            else puts("No cycle found.");
        }
        return 0;
    }
  • 相关阅读:
    SQL面试题集合
    绕过UAC提示以管理员身份运行程序
    一个在VS2010中不能加载项目的问题
    Windows下硬链接、软链接和快捷方式的区别
    自动化测试中FindWindow与FindWindowEx的使用示例
    在C#中调用批处理文件
    windows的自动登陆问题
    PowerShell操作XML遇到的问题
    MySQL集群MGR架构for单主模式
    MySQL集群MGR架构for多主模式
  • 原文地址:https://www.cnblogs.com/rootial/p/3404069.html
Copyright © 2020-2023  润新知