[Hdu2055] better off big money (the best match)

Problem Description
Legend in faraway places have a very wealthy village, one day, the mayor decided to carry out institutional reforms: re-distribution house.
This is a major event in relation to the housing problems of the people ah. In the village there are n rooms, there are n just ordinary people, taking into account every household should have room to live (if there are people out of homes, it is easy to cause unrest), each must be assigned to a house and can only get a house.
On the other hand, the village chief and other village leaders hope to get the maximum benefit, this village institutions will have the money. Because people are more prosperous, they can each house a certain price within the range of their economic , for example, there are three houses, one can people out 100,000 pairs between the first, the first two out of 20,000, to 200,000 between the first three. (of course, within the scope of their economy). now the problem is that village how to lead the largest distribution house to make income. (the villagers even have money to buy a house, but not necessarily be able to buy, look at the distribution of village leaders).
Input
Comprising a plurality of sets of test input data, a first data input line of each n, represents the number of (the number of people are at home) of the house, then there are n rows, each row number n i denotes the j th village name the room price (n <= 300).
 
Output
Please deliver maximum revenue values ​​for each set of data, each set of output per line.
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<algorithm>
#define re return
#define ll long long
#define inc(i,l,r) for(int i=l;i<=r;++i)

const int inf=2147483647,maxn=305;
using namespace std;
template<typename T>inline void rd(T&x)
{
    char c;bool f=0;
    while((c=getchar())<' 0 ' || C> ' . 9 ' ) IF (C == ' - ' ) F = . 1 ; 
    X = C ^ 48 ;
     the while ((C = getchar ())> = ' 0 ' && C <= ' . 9 ' ) X = X * 10 + (C ^ 48 );
     IF (F) = X - X; 
} 

int n-;
 int EX1 [MAXN]; // desired degree. 1 
int EX2 [MAXN]; // desirability 2 
int PRI [MAXN] [MAXN]; // price
int match [MAXN]; // matching 2 1 
int VIS1 [MAXN]; // if 1 is accessed 
int VIS2 [MAXN]; // 2 you visited 
int Slack [MAXN]; // minimum difference number, 2 1 may be accessed 

inline BOOL DFS ( int X) 
{ 
    VIS1 [X] = 1 ; // tag 1 access 
    inc is (I, 1 , n-) 
    { 
        IF (VIS2 [I]) Continue ;
         IF (EX1 [X] + EX2 [I] == PRI [X] [I]) // achieve access requirements 
        { 
            VIS2 [I] = . 1; Access tag 2
             IF (match [I] ||! DFS (match [I])) 
            { 
                match [I] = X; 
                Re . 1 ; 
            } 
        } 
        the else Slack [I] = min (Slack [I], EX1 [X ] + EX2 [I] - PRI [X] [I]);
 // 2 statistical difference 
    } 
    Re 0 ; 
} 

inline void KM () 
{ 
    inc is (I, . 1 , n-) match [I] = EX2 [I] = 0 ;
 // refresh 
    inc is (I, . 1 , n-) 
    { 
        inc is (J, . 1 , n-) 
        Slack [J]=inf;
        while(2333)
        {
            inc(j,1,n)vis1[j]=vis2[j]=0;
            if(dfs(i))break;
            int d=inf;
            inc(j,1,n)
            if(!vis2[j])
                d=min(d,slack[j]); 
//最小改变度
            inc(j,1,n)
            {
                if(vis1[j])ex1[j]-=d;
                if(vis2[j])ex2[j]+=d;
                else slack[j]-=d;
//分别改变
            }
        }
    }
}

int main()
{
    while(~scanf("%d",&n))
    {
        
        inc(i,1,n)ex1[i]=-inf;
        inc(i,1,n)    
        inc(j,1,n)
        {
            rd(pri[i][j]);
            ex1[i]=max(ex1[i],pri[i][j]);
        }
        int ans=0;
        KM();
        for(int i=1;i<=n;++i)
        ans+=pri[match[i]][i];
        printf("%d\n",ans);
    }

    
    re 0;
}

 

Guess you like

Origin www.cnblogs.com/lsyyy/p/11366195.html