zoukankan      html  css  js  c++  java
  • hdu5988最小费用最大流浮点

    惊了,TLE半天发现浮点运算是要加esp,真是学到了。

    题目链接https://www.nowcoder.com/acm/contest/207/G

    题意就是给你N个点,每个点有si个人和bi个食物背包,然后是M条边,每条边有个触电概率pi,第一个人经过这条边不会触电,问你让所有人吃完饭的最小触电概率.

    方法:如果si>bi 连接0到i 容量为si-bi,费用为0,否则就连接 i到n+1,容量为bi-si,费用为0

    然后把每线路拆成两条,一条容量为1,费用为0,一条容量为c-1,费用为-log(1-pi)

    因为最后要输出所有概率的乘积的最小值,取对数后变成负数,加上负号后最小变最大,所以再把概率取反变成(1-pi)

    跑一边最短路输出1-exp(-ans)即可

    #include<bits/stdc++.h>
    #define esp 1e-7
    using namespace std;
    const int maxn=205;
    const int INF=0x3fffffff;
    struct Edge
    {
        int from,to,cap,flow;
        double cost;
    };
    struct MCMF
    {
        int n,m,s,t;
        vector<Edge>edges;
        vector<int> G[maxn];
        int inq[maxn];
        double d[maxn];
        int p[maxn];
        int a[maxn];
        void init(int n)
        {
            this->n=n;
            for(int i=0; i<=n; i++)G[i].clear();
            edges.clear();
        }
        void AddEdge(int from,int to,int cap,double cost)
        {
            Edge e;
            e.from=from,e.to=to,e.cap=cap,e.flow=0,e.cost=cost;
            edges.push_back(e);
            e.from=to,e.to=from,e.cap=0,e.flow=0,e.cost=-cost;
            edges.push_back(e);
            m=edges.size();
            G[from].push_back(m-2);
            G[to].push_back(m-1);
        }
        bool BellmanFord(int s,int t,int& flow,double& cost)
        {
            for(int i=0; i<=n; i++)d[i]=INF;
            memset(inq,0,sizeof(inq));
            d[s]=0;
            inq[s]=1;
            p[s]=0;
            a[s]=INF;
    
            queue<int>Q;
            Q.push(s);
            while(!Q.empty())
            {
                int u=Q.front();
                Q.pop();
                inq[u]=0;
                for(int i=0; i<(int)G[u].size(); i++)
                {
                    Edge& e=edges[G[u][i]];
                    if(e.cap>e.flow&&d[e.to]-d[u]-e.cost>esp)
                    {
                        d[e.to]=d[u]+e.cost;
                        p[e.to]=G[u][i];
                        a[e.to]=min(a[u],e.cap-e.flow);
                        if(!inq[e.to])
                        {
                            Q.push(e.to);
                            inq[e.to]=1;
                        }
                    }
                }
            }
            if(d[t]==INF)return false;
            flow+=a[t];
            cost+=d[t]*a[t];
            int u=t;
            while(u!=s)
            {
                edges[p[u]].flow+=a[t];
                edges[p[u]^1].flow-=a[t];
                u=edges[p[u]].from;
            }
            return true;
        }
        double Mincost(int s,int t)
        {
            int flow=0;
            double cost=0;
            while(BellmanFord(s,t,flow,cost));
            return cost;
        }
    } mcmf;
    
    int main()
    {
        int t,n,m,s,b,u,v,c;
        double pi;
        scanf("%d",&t);
        while(t--)
        {
            scanf("%d%d",&n,&m);
            mcmf.init(n+2);
            for (int i=1; i<=n ; i++ )
            {
                scanf("%d%d",&s,&b);
                if(s>b)
                {
                    mcmf.AddEdge(0,i,s-b,0);
                }
                else if(b>s)
                {
                    mcmf.AddEdge(i,n+1,b-s,0);
                }
            }
            for (int i=1; i<=m ; i++ )
            {
                scanf("%d%d%d%lf",&u,&v,&c,&pi);
                if(c>0)mcmf.AddEdge(u,v,1,0);
                if(c-1>0)
                {
                    mcmf.AddEdge(u,v,c-1,-log(1.0-pi));
                }
            }
            printf("%.2lf
    ",1.0-exp(-mcmf.Mincost(0,n+1)));
        }
        return 0;
    }
  • 相关阅读:
    Java基础多线程之后台守护线程,setDaemon(true)
    Java基础多线程间通讯之多生产者、多消费者模式示例:
    Java基础多线程通讯之生产者消费者模式示例:
    Java基础多线程之单例模式之懒汉式:
    Java基础多线程间通讯同步操作示例一(未优化):
    Java基础多线程之线程中止示例:
    Java基础多线程之join抢夺CPU执行权直到该线程结束。
    Java基础多线程之单例模式之饿汉式:
    Java基础多线程间通讯示例操作(已优化)二:
    Java基础多线程之实际开发中常见写法:
  • 原文地址:https://www.cnblogs.com/Json-Five/p/9751026.html
Copyright © 2011-2022 走看看