以前用KM写过,现在再用费用流写。

  1. #include <iostream>
  2. #include <cstdio>
  3. #include <cstring>
  4. #include <queue>
  5. #include <vector>
  6. #include <utility>
  7. #define abs(a) ((a)<0?-(a):(a))
  8. #define maxn 210
  9. #define oo 0x3f3f3f3f
  10. using namespace std;
  11.  
  12. struct Edge {
  13. int u, v, c, f;
  14. Edge( int u, int v, int c, int f ):u(u),v(v),c(c),f(f){}
  15. };
  16. struct Mcmf {
  17. int n, src, dst;
  18. vector<Edge> edge;
  19. vector<int> g[maxn];
  20. int dis[maxn], pth[maxn], ext[maxn];
  21.  
  22. void init( int n, int src, int dst ) {
  23. this->n = n;
  24. this->src = src;
  25. this->dst = dst;
  26. for( int i=; i<=n; i++ )
  27. g[i].clear();
  28. edge.clear();
  29. }
  30. void add_edge( int u, int v, int c, int f ) {
  31. g[u].push_back( edge.size() );
  32. edge.push_back( Edge(u,v,c,f) );
  33. g[v].push_back( edge.size() );
  34. edge.push_back( Edge(v,u,-c,) );
  35. }
  36. bool spfa( int &flow, int &cost ) {
  37. queue<int> qu;
  38. memset( dis, 0x3f, sizeof(dis) );
  39. qu.push( src );
  40. ext[src] = true;
  41. dis[src] = ;
  42. pth[src] = -;
  43. while( !qu.empty() ) {
  44. int u=qu.front();
  45. qu.pop();
  46. ext[u] = false;
  47. for( int t=; t<g[u].size(); t++ ) {
  48. Edge &e = edge[g[u][t]];
  49. if( e.f && dis[e.v]>dis[e.u]+e.c ) {
  50. dis[e.v] = dis[e.u]+e.c;
  51. pth[e.v] = g[u][t];
  52. if( !ext[e.v] ) {
  53. ext[e.v] = true;
  54. qu.push( e.v );
  55. }
  56. }
  57. }
  58. }
  59. if( dis[dst]==oo ) return false;
  60. int flw = oo;
  61. for( int eid=pth[dst]; eid!=-; eid=pth[edge[eid].u] )
  62. flw = min( flw, edge[eid].f );
  63. for( int eid=pth[dst]; eid!=-; eid=pth[edge[eid].u] ) {
  64. edge[eid].f -= flw;
  65. edge[eid^].f += flw;
  66. }
  67. flow += flw;
  68. cost += flw*dis[dst];
  69. return true;
  70. }
  71. void mcmf( int &flow, int &cost ) {
  72. flow = cost = ;
  73. while( spfa(flow,cost) );
  74. }
  75. };
  76.  
  77. int n, m;
  78. int aa[maxn][], bb[maxn][], ta, tb;
  79. Mcmf M;
  80.  
  81. int main() {
  82. ios::sync_with_stdio( false );
  83. while() {
  84. cin>>n>>m;
  85. if( n== && m== ) return ;
  86. ta = tb = ;
  87. for( int i=; i<=n; i++ )
  88. for( int j=; j<=m; j++ ) {
  89. char ch;
  90. cin>>ch;
  91. if( ch=='m' ) {
  92. ta++;
  93. aa[ta][] = i;
  94. aa[ta][] = j;
  95. } else if( ch=='H' ) {
  96. tb++;
  97. bb[tb][] = i;
  98. bb[tb][] = j;
  99. }
  100. }
  101. M.init( ta+tb+, ta+tb+, ta+tb+ );
  102. for( int i=; i<=ta; i++ )
  103. M.add_edge( M.src, i, , );
  104. for( int j=ta+; j<=ta+tb; j++ )
  105. M.add_edge( j, M.dst, , );
  106. for( int i=; i<=ta; i++ )
  107. for( int j=ta+; j<=ta+tb; j++ ) {
  108. int dis = abs(aa[i][]-bb[j-ta][])+abs(aa[i][]-bb[j-ta][]);
  109. M.add_edge( i, j, dis, );
  110. }
  111. int flow, cost;
  112. M.mcmf( flow, cost );
  113. cout<<cost<<endl;
  114. }
  115. }

hdu 1533 KM或费用流的更多相关文章

  1. HDU 3488--Tour(KM or 费用流)

    因为每个点只能经过一次 所以考虑拆点 这题有坑,有重边.. KM算法 把一个点拆成入点和出点 入点在X部,出点在Y步. 如果u,v之间有路径,就在X部的u点连接Y部的v点 求完美匹配. 当完美匹配的时 ...

  2. POJ 2195 Going Home / HDU 1533(最小费用最大流模板)

    题目大意: 有一个最大是100 * 100 的网格图,上面有 s 个 房子和人,人每移动一个格子花费1的代价,求最小代价让所有的人都进入一个房子.每个房子只能进入一个人. 算法讨论: 注意是KM 和 ...

  3. HDU 5988 Coding Contest(费用流+浮点数)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5988 题目大意: 给定n个点,m条有向边,每个点是一个吃饭的地方,每个人一盒饭.每个点有S个人,有B盒 ...

  4. POJ 2135 Farm Tour &amp;&amp; HDU 2686 Matrix &amp;&amp; HDU 3376 Matrix Again 费用流求来回最短路

    累了就要写题解,近期总是被虐到没脾气. 来回最短路问题貌似也能够用DP来搞.只是拿费用流还是非常方便的. 能够转化成求满流为2 的最小花费.一般做法为拆点,对于 i 拆为2*i 和 2*i+1.然后连 ...

  5. Going Home HDU - 1533(最大费用最小流)

    On a grid map there are n little men and n houses. In each unit time, every little man can move one ...

  6. HDU 1533 KM算法(权值最小的最佳匹配)

    Going Home Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total ...

  7. HDU 3315 My Brute(费用流)

    职务地址:HDU 3315 这个题的思路全然是自己想出来的,自我感觉挺巧妙的. . .(大牛勿喷.. . )对大胆建图又多了一份信心. 详细思路是构造一个二分图,Si连源点.Xi连汇点,流量都是1,费 ...

  8. HDU 2686 Matrix(最大费用流)

    Matrix Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Sub ...

  9. HDU 1533 & KM模板

    题意 求二分图最小完备匹配. SOL 建个图那么方便的事情是吧...然后边权都是正的(好像根边权也没什么关系),既然要求最小那么把边权取个相反数跑个KM就好了.. CODE: /*========== ...

随机推荐

  1. NB二人组(一)----堆排序

    堆排序前传--树与二叉树简介 特殊且常用的树--二叉树  两种特殊的二叉树 二叉树的存储方式 二叉树小结 堆排序 堆这个玩意....... 堆排序过程: 构造堆: 堆排序的算法程序(程序需配合着下图理 ...

  2. 巅峰极客CTF writeup[上]

    经验教训 1.CTF不比实战,最好不要死磕.死磕就输了.我就是死磕在缓存文件死的.真的惭愧: 2.对于flag的位置不要太局限于web目录下,如果是命令执行直接上find / -name flag*: ...

  3. 64_t5

    texlive-mkpattern-svn15878.1.2-33.fc26.2.noarch..> 24-May-2017 15:54 38178 texlive-mkpic-bin-svn3 ...

  4. MySQL删除数据几种情况以及是否释放磁盘空间【转】

    MySQL删除数据几种情况以及是否释放磁盘空间: 1.drop table table_name 立刻释放磁盘空间 ,不管是 Innodb和MyISAM ; 2.truncate table tabl ...

  5. openstack环境下的虚拟机通过浮动IP访问后能ping通外网IP不能ping通域名

    1.环境简介 openstack环境下构造Ubuntu系统的VM,VM配置受管子网和自管子网,同时绑定浮动IP 2.通过浮动IP访问VM后,ping www.baidu.com失败,但是通过IP地址p ...

  6. JNDI(Java Naming and Directory Interface,Java命名和目录接口)

    JNDI(Java Naming and Directory Interface,Java命名和目录接口)是SUN公司提供的一种标准的Java命名系统接口,JNDI提供统一的客户端API,通过不同的访 ...

  7. 根据名字杀死进程Killall

    Killall命令可以用来给一个特定的进程发送一个信号.这个信号默认情况下是SIGTERM,但也可以由killall命令使用参数来指定其它信号.现在让我们通过一些实际的例子来看看这个命令的实际用法. ...

  8. plsql例子

    create or replace procedure find_difference(db_link in varchar2) is /* 比对两套环境建表脚本差异,以224环境为主 当前环境,db ...

  9. HDU 4725 The Shortest Path in Nya Graph(spfa+虚拟点建图)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4725 题目大意:有n层,n个点分布在这些层上,相邻层的点是可以联通的且距离为c,还有额外给出了m个条边 ...

  10. mongodb与mysql传统的关系数据库区别

    转自:易百教程 MongoDB中的数据具有灵活的模式.文档在同一集合,但它们不需要具有相同的字段或结构集合,集合文档中的公共字段可以包含不同类型的数据. MongoDB中的数据具有灵活的模式.与SQL ...