zoukankan      html  css  js  c++  java
  • 小行星

    个人认为思维难度比较大。

    看到这题,我们要想办法将其转化为最小割。

    考虑到割x,y,z都能完成任务,我们将其并联,割掉其中任意一边都行。

    因为割得是权,于是以权为点,而不是以节点为点。

    并且要拆点。

    超级源点向x连边,x向y的入口连边,y的入口向出口连边,y的出口向z连边,z向超级汇点连边。

    看代码:

    #include<bits/stdc++.h>
    using namespace std;
    #define inf 1e9
    const int maxn=2020;
    const int maxm=1e5+10;
    int p[maxn][maxn];
    int n,dep[maxn];
    struct node{
        int x,y,z;
    }a[maxm];
    queue<int>q;
    inline int bfs(){
        memset(dep,0x3f,sizeof(dep));
        while(!q.empty())q.pop();
        dep[0]=0;
        q.push(0);
        while(!q.empty()){
            int x=q.front();
            q.pop();
            for(int i=0;i<=2001;i++)
                if(p[x][i]&&dep[i]>10000){
                    dep[i]=dep[x]+1;
                    q.push(i);
                }
        }
        return dep[2001]<10000;
    }
    inline int dfs(int x,int lim){
        if(x==2001||!lim)return lim;
        int ans=0;
        for(int i=0;i<=2001;i++)
            if(p[x][i]&&dep[i]==dep[x]+1){
                int f=dfs(i,min(p[x][i],lim));
                lim-=f;ans+=f;
                p[x][i]-=f;p[i][x]+=f;
            }
        return ans;
    }
    int main(){
        cin>>n;
        for(int i=1;i<=n;i++)
            scanf("%d%d%d",&a[i].x,&a[i].y,&a[i].z);
        for(int i=1;i<=n;i++){
            p[0][a[i].x]=1;
            p[a[i].x][a[i].y+500]=inf;
            p[a[i].y+500][a[i].y+1000]=1;
            p[a[i].y+1000][a[i].z+1500]=inf;
            p[a[i].z+1500][2001]=1;
        }
        int maxflow=0;
        while(bfs())maxflow+=dfs(0,inf);
        printf("%d
    ",maxflow);
        return 0;
    }

    深深地感到自己的弱小。

  • 相关阅读:
    RecyclerView的万能适配器+定义可以到底部自动刷新的RecyclerView
    Material Design 摘要
    模版方法模式
    工厂方法模式
    单例模式
    Android中使用Intent和IntentFilter进行通信
    Json/XML/HTML数据解析
    Java中集合总结
    重构笔记
    Android中ActionBar的使用
  • 原文地址:https://www.cnblogs.com/syzf2222/p/12430744.html
Copyright © 2011-2022 走看看