Submission #1400919

#TimeUsernameProblemLanguageResultExecution timeMemory
1400919tung04885Selotejp (COCI20_selotejp)C++20
110 / 110
1 ms1348 KiB
#include <bits/stdc++.h>
using namespace std;
#define ll long long
#define pii pair<int,int>
#define pll pair<ll,ll>
#define fi first
#define se second
#define all(a) (a).begin(),(a).end()
#define __buitin_popcount __builtin_popcountll
#define BIT(x,i) (((x)>>(i))&1ll)
#define MASK(i) (1ll<<(i))

template<class X,class Y> bool maximize(X &x,Y y)
{
    if(x<y)
    {
        x=y;
        return 1;
    }
    return 0;
}

template<class X,class Y> bool minimize(X &x,Y y)
{
    if(y<x)
    {
        x=y;
        return 1;
    }
    return 0;
}

const int inf=1e9+412009;
const ll INF=2e18+412009;

struct KUHN_MATCHING
{
    int n,m;
    vector<vector<int>> adj;
    vector<int> d,vis;
    vector<int> Match_l,Match_r;
    int dm;

    KUHN_MATCHING(int _n=0,int _m=0)
    {
        n=_n;
        m=_m;

        adj.resize(n+1);
        d.resize(n+1);
        vis.resize(n+1);
        Match_l.resize(n+1);
        Match_r.resize(m+1);
    }

    void addEdge(int u,int v)
    {
        adj[u].push_back(v);
    }

    bool dfs(int u)
    {
        if(vis[u]==dm) return 0;
        vis[u]=dm;

        for(int v:adj[u])
        {
            if(Match_r[v]==-1)
            {
                Match_l[u]=v;
                Match_r[v]=u;
                return 1;
            }
            if(d[Match_r[v]]==d[u]+1&&dfs(Match_r[v]))
            {
                Match_l[u]=v;
                Match_r[v]=u;
                return 1;
            }
        }

        return 0;
    }

    int MaxMatching()
    {
        dm=0;
        for(int i=1;i<=n;i++)
        {
            Match_l[i]=-1;
            vis[i]=0;
        }
        for(int i=1;i<=m;i++) Match_r[i]=-1;

        int totmatching=0;

        while(true)
        {
            queue<int> q;

            for(int i=1;i<=n;i++) if(Match_l[i]==-1)
            {
                q.push(i);
                d[i]=0;
            }
            else d[i]=-1;

            while(!q.empty())
            {
                int u=q.front();
                q.pop();

                for(int v:adj[u])
                {
                    if(Match_r[v]!=-1&&d[Match_r[v]]==-1)
                    {
                        d[Match_r[v]]=d[u]+1;
                        q.push(Match_r[v]);
                    }
                }
            }

            int tot=0;

            for(int i=1;i<=n;i++) if(Match_l[i]==-1)
            {
                dm++;
                tot+=dfs(i);
            }

            if(tot==0) break;
            totmatching+=tot;
        }

        return totmatching;
    }
};

int m,n;
char a[1010][12];
int vl=0;

void nhap()
{
    cin>>m>>n;

    for(int i=1;i<=m;i++) for(int j=1;j<=n;j++)
        cin>>a[i][j],vl+=a[i][j]=='#';
}

KUHN_MATCHING graph;
int f[1010][12][2];

void solve()
{
    int cnt=0;
    for(int i=1;i<=m;i++) for(int j=1;j<=n;j++) if(a[i][j]=='#')
    {
        if(i+1<=m&&a[i+1][j]=='#') f[i][j][0]=++cnt;
        if(j+1<=n&&a[i][j+1]=='#') f[i][j][1]=++cnt;
    }

    graph=KUHN_MATCHING(cnt,cnt);

    for(int i=1;i<=m;i++) for(int j=1;j<n;j++) if(a[i][j]=='#'&&a[i][j+1]=='#')
    {
        if(i-1>0)
        {
            if(a[i-1][j]=='#') graph.addEdge(f[i][j][1],f[i-1][j][0]);
            if(a[i-1][j+1]=='#') graph.addEdge(f[i][j][1],f[i-1][j+1][0]);
        }
        if(i+1<=m)
        {
            if(a[i+1][j]=='#') graph.addEdge(f[i][j][1],f[i][j][0]);
            if(a[i+1][j+1]=='#') graph.addEdge(f[i][j][1],f[i][j+1][0]);
        }
    }

    cout<<vl-(cnt-graph.MaxMatching());
}

int main()
{
    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);cout.tie(nullptr);


    nhap();
    solve();

    return 0;
}
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...