CF 316C2(Tidying Up-二分图最大边权)
4 seconds
256 megabytes
standard input
standard output
Smart Beaver is careful about his appearance and pays special attention to shoes so he has a huge number of pairs of shoes from the most famous brands of the forest. He's trying to handle his shoes carefully so that each pair stood side by side. But by the end of the week because of his very active lifestyle in his dressing room becomes a mess.
Smart Beaver from ABBYY is not only the brightest beaver in the area, but he also is the most domestically oriented. For example, on Mondays the Smart Beaver cleans everything in his home.
It's Monday morning. Smart Beaver does not want to spend the whole day cleaning, besides, there is much in to do and it’s the gym day, so he wants to clean up as soon as possible. Now the floors are washed, the dust is wiped off — it’s time to clean up in the dressing room. But as soon as the Smart Beaver entered the dressing room, all plans for the day were suddenly destroyed: chaos reigned there and it seemed impossible to handle, even in a week. Give our hero some hope: tell him what is the minimum number of shoes need to change the position to make the dressing room neat.
The dressing room is rectangular and is divided into n × m equal squares, each square contains exactly one shoe. Each pair of shoes has a unique number that is integer from 1 to , more formally, a square with coordinates (i, j) contains an integer number of the pair which is lying on it. The Smart Beaver believes that the dressing room is neat only when each pair of sneakers lies together. We assume that the pair of sneakers in squares (i1, j1) and (i2, j2) lies together if |i1 - i2| + |j1 - j2| = 1.
The first line contains two space-separated integers n and m. They correspond to the dressing room size. Next n lines contain m space-separated integers each. Those numbers describe the dressing room. Each number corresponds to a snicker.
It is guaranteed that:
- n·m is even.
- All numbers, corresponding to the numbers of pairs of shoes in the dressing room, will lie between 1 and
.
- Each number from 1 to
will occur exactly twice.
The input limits for scoring 30 points are (subproblem C1):
- 2 ≤ n, m ≤ 8.
The input limits for scoring 100 points are (subproblems C1+C2):
- 2 ≤ n, m ≤ 80.
Print exactly one integer — the minimum number of the sneakers that need to change their location.
2 3
1 1 2
2 3 3
2
3 4
1 3 2 6
2 1 5 6
4 4 5 3
4
The second sample.转换为2分图最大边权费用流。
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<functional>
#include<cmath>
#include<cctype>
using namespace std;
#define For(i,n) for(int i=1;i<=n;i++)
#define Rep(i,n) for(int i=0;i<n;i++)
#define Fork(i,k,n) for(int i=k;i<=n;i++)
#define ForD(i,n) for(int i=n;i;i--)
#define Forp(x) for(int p=pre[x];p;p=next[p])
#define RepD(i,n) for(int i=n;i>=0;i--)
#define MAXN (80*80+10)
#define MAXL (80+10)
#define MAXM (MAXL*MAXL*4+MAXN*4)
#define INF (2139062143)
int q[MAXN*8],d[MAXN],pr[MAXN],ed[MAXN],b[MAXN];
int edge[MAXM],next[MAXM],cost[MAXM],weight[MAXM],pre[MAXN],size=1;
void addedge(int u,int v,int w,int c)
{
edge[++size]=v;
weight[size]=w;
cost[size]=c;
next[size]=pre[u];
pre[u]=size;
}
void addedge2(int u,int v,int w,int c){addedge(u,v,w,c),addedge(v,u,0,-c);}
bool SPFA(int s,int t)
{
memset(d,127,sizeof(d));
memset(b,0,sizeof(b));
d[q[1]=s]=0;b[s]=1;
int head=1,tail=1;
while (head<=tail)
{
int now=q[head++];
Forp(now)
{
int &v=edge[p];
if (weight[p]&&d[now]+cost[p]<d[v])
{
d[v]=d[now]+cost[p];
if (!b[v]) b[v]=1,q[++tail]=v;
pr[v]=now,ed[v]=p;
}
}
b[now]=0;
}
return d[t]<d[0];
}
int CostFlow(int s,int t)
{
int totcost=0;
while (SPFA(s,t))
{
int flow=INF;
for(int x=t;x^s;x=pr[x]) flow=min(flow,weight[ed[x]]);
totcost+=flow*d[t];
for(int x=t;x^s;x=pr[x]) weight[ed[x]]-=flow,weight[ed[x]^1]+=flow;
}
return totcost;
}
int n,m,a[MAXL][MAXL];
int no(int i,int j){return (i-1)*m+j;}
int main()
{
// freopen(".in","r",stdin);
// freopen(".out","w",stdout);
cin>>n>>m;
int s=n*m+1,t=n*m+2;
For(i,n) For(j,m) cin>>a[i][j];
For(i,n) For(j,m)
{
if (i+j&1) addedge2(s,no(i,j),1,0);
else addedge2(no(i,j),t,1,0);
if (j<m)
{
if (i+j&1) addedge2(no(i,j),no(i,j+1),1,a[i][j]!=a[i][j+1]);
else addedge2(no(i,j+1),no(i,j),1,a[i][j]!=a[i][j+1]);
}
if (i<n)
{
if (i+j&1) addedge2(no(i,j),no(i+1,j),1,a[i][j]!=a[i+1][j]);
else addedge2(no(i+1,j),no(i,j),1,a[i][j]!=a[i+1][j]);
}
}
cout<<CostFlow(s,t)<<endl;
return 0;
}
CF 316C2(Tidying Up-二分图最大边权)的更多相关文章
- POJ 2125 Destroying the Graph 二分图最小点权覆盖
Destroying The Graph Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 8198 Accepted: 2 ...
- POJ2125 Destroying The Graph(二分图最小点权覆盖集)
最小点权覆盖就是,对于有点权的有向图,选出权值和最少的点的集合覆盖所有的边. 解二分图最小点权覆盖集可以用最小割: vs-X-Y-vt这样连边,vs和X部点的连边容量为X部点的权值,Y部和vt连边容量 ...
- POJ 2125 Destroying The Graph (二分图最小点权覆盖集+输出最小割方案)
题意 有一个图, 两种操作,一种是删除某点的所有出边,一种是删除某点的所有入边,各个点的不同操作分别有一个花费,现在我们想把这个图的边都删除掉,需要的最小花费是多少. 思路 很明显的二分图最小点权覆盖 ...
- POJ 2125 Destroying The Graph 二分图 最小点权覆盖
POJ2125 题意简述:给定一个有向图,要通过某些操作删除所有的边,每一次操作可以选择任意一个节点删除由其出发的所有边或者通向它的所有边,两个方向有不同的权值.问最小权值和的解决方案,要输出操作. ...
- HDU1565 方格取数(1) —— 状压DP or 插头DP(轮廓线更新) or 二分图点带权最大独立集(最小割最大流)
题目链接:https://vjudge.net/problem/HDU-1565 方格取数(1) Time Limit: 10000/5000 MS (Java/Others) Memory L ...
- POJ2125 Destroying The Graph 二分图 + 最小点权覆盖 + 最小割
思路来源:http://blog.csdn.net/lenleaves/article/details/7873441 求最小点权覆盖,同样求一个最小割,但是要求出割去了那些边, 只要用最终的剩余网络 ...
- hdu 1829 &poj 2492 A Bug's Life(推断二分图、带权并查集)
A Bug's Life Time Limit: 15000/5000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) To ...
- poj 3308 Paratroopers(二分图最小点权覆盖)
Paratroopers Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 8954 Accepted: 2702 Desc ...
- HDU1569 方格取数(2) —— 二分图点带权最大独立集、最小割最大流
题目链接:https://vjudge.net/problem/HDU-1569 方格取数(2) Time Limit: 10000/5000 MS (Java/Others) Memory L ...
随机推荐
- GTest交流与经验总结
GTest交流与经验总结 原文见: http://starsourcingsolutions.com/myblog/?p=159
- 使用链表实现队列------《数据结构与算法分析-C语言描述》
经过ubuntu的gcc验证 一.头文件 que_link.h #ifndef _QUE_LINK_H_ #define _QUE_LINK_H_ struct que_record; typedef ...
- SSH2三大框架整合警告
*********************************************************************** * WARNING!!! * * * * >> ...
- 托管到GitHub
如何把项目托管到GitHub iOS开发拓展篇——如何把项目托管到GitHub 说明:本文主要介绍如何把一个OC项目托管到Github,重操作轻理论. 第一步:先注册一个Github的账号,这是必须的 ...
- QT update和repaint的区别
void QWidget::repaint ( int x, int y, int w, int h, bool erase = TRUE ) [槽] 通过立即调用paintEvent()来直接重新绘 ...
- DataTable的一些使用技巧
在做机房的时候经常用到DataTable,发现如果DataTable使用的好的话,不仅能使程序简洁实用,而且能够提高性能,达到事半功倍的效果.现在对我知道的一些技巧做个总结,虽然都是一些简单的,但是发 ...
- webdynpro 下拉列表控件
现在界面上添加下拉列表的控件DropDownByKey 在context中创建新的node,和属性DP 返回界面,绑定DP到控件DropDownByKey的SelectedKey 初始方法中代码如下: ...
- Servlet的学习之Session(1)
在学习完了Servlet中的Cookie技术后,我们再来学习另一个能保存会话数据的技术——Session. Session是服务器端技术,利用这个技术,服务器在运行时可以为每一个用户的浏览器创建一个其 ...
- 【Demo 0009】Java基础-异常
本章学习要点: 1. 了解异常的基本概念: 2. 掌握异常捕获方法以及注意事项; 3. 掌握异常抛出方法: 4. 掌握自定义异常类和异常类继承注 ...
- leetcode Sum Root to Leaf Numbers(所有路径之和)
转载请注明来自souldak,微博:@evagle 观察题目给的返回值类型是int,可以断定这棵树的高度不会超过10,所以数据量其实是非常小的.那就直接dfs遍历这棵树,然后到叶子节点的时候将值加到最 ...