Going Home
Time Limit: 1000MS   Memory Limit: 65536K
Total Submissions: 15944   Accepted: 8167

Description

On a grid map there are n little men and n houses. In each unit time, every little man can move one unit step, either horizontally, or vertically, to an adjacent point. For each little man, you need to pay a $1 travel fee for every step he moves, until he enters a house. The task is complicated with the restriction that each house can accommodate only one little man.

Your task is to compute the minimum amount of money you need to pay in order to send these n little men into those n different houses. The input is a map of the scenario, a '.' means an empty space, an 'H' represents a house on that point, and am 'm' indicates there is a little man on that point.

You can think of each point on the grid map as a quite large square, so it can hold n little men at the same time; also, it is okay if a little man steps on a grid with a house without entering that house.

Input

There are one or more test cases in the input. Each case starts with a line giving two integers N and M, where N is the number of rows of the map, and M is the number of columns. The rest of the input will be N lines describing the map. You may assume both N and M are between 2 and 100, inclusive. There will be the same number of 'H's and 'm's on the map; and there will be at most 100 houses. Input will terminate with 0 0 for N and M.

Output

For each test case, output one line with the single integer, which is the minimum amount, in dollars, you need to pay.

Sample Input

2 2
.m
H.
5 5
HH..m
.....
.....
.....
mm..H
7 8
...H....
...H....
...H....
mmmHmmmm
...H....
...H....
...H....
0 0

Sample Output

2
10
28

Source

 
题意:

给定一个N*M的地图,地图上有若干个man和house,且man与house的数量一致。man每移动一格需花费$1(即单位费用=单位距离),一间house只能入住一个man。现在要求所有的man都入住house,求最小费用。

man可以从house上跨过

 
思路:
 
模板题   建图之后 直接套最小费用流模板
 
#include <stdio.h>
#include <iostream>
#include <string.h>
#include<cmath>
using namespace std;
const int N=300;
const int MAXE=200000;
const int inf=1<<30;
int head[N],ep;
int d[N],pre[N];
bool vis[N];
int q[MAXE];
struct Edge
{
int u,v,c,w,next;
}edge[MAXE];
void addedge(int u,int v,int w,int c)//u v 费用 容量
{
edge[ep].u=u;
edge[ep].v=v;
edge[ep].w=w;
edge[ep].c=c;
edge[ep].next=head[u];
head[u]=ep++;
edge[ep].v=u;
edge[ep].u=v;
edge[ep].w=-w;
edge[ep].c=0;
edge[ep].next=head[v];
head[v]=ep++;
}
int SPFA(int src,int des)
{
int l,r;
memset(pre,-1,sizeof(pre));
memset(vis,0,sizeof(vis));
for(int i=0;i<=des;i++) d[i]=inf;
d[src]=0;
l=0;r=0;
q[r++]=src;
vis[src]=1;
while(l<r)
{
int u=q[l++];
vis[u]=0;
for(int j=head[u];j!=-1;j=edge[j].next)
{
int v=edge[j].v;
if(edge[j].c>0&&d[u]+edge[j].w<d[v])
{
d[v]=d[u]+edge[j].w;
pre[v]=j;
if(!vis[v])
{
vis[v]=1;
q[r++]=v;
}
}
}
}
if(d[des]==inf)
return 0;
return 1;
}
int MCMF(int src,int des)
{
int flow=0,ans=0;//flow是得到的最大流的值 ans得到的是最小的费用
while(SPFA(src,des))
{
ans+=d[des];
int u=des;
int mini=inf;
while(u!=src)
{
if(edge[pre[u]].c<mini)
mini=edge[pre[u]].c;
u=edge[pre[u]].u;
}
flow+=mini;
u=des;
while(u!=src)
{
edge[pre[u]].c-=mini;
edge[pre[u]^1].c+=mini;
u=edge[pre[u]].u;
}
}
return ans;
}
///以上为模板
struct man
{
int x;
int y;
}M[111];
struct house
{
int x,y;
}H[111];
char str[111];
int main()
{
int n,m,mcnt,hcnt,i,j,src,des;
while(scanf("%d%d",&n,&m)!=EOF)
{
if(!n&&!m) break;
ep=0;
memset(head,-1,sizeof(head));
mcnt=hcnt=0;
for(i=0;i<n;i++)
{
scanf("%s",str);
for(j=0;j<m;j++)
{
if(str[j]=='H')
{
hcnt++;
H[hcnt].x=i; H[hcnt].y=j;
}
else if(str[j]=='m')
{
mcnt++;
M[mcnt].x=i; M[mcnt].y=j;
}
}
}
for(i=1;i<=mcnt;i++)
{
for(j=1;j<=hcnt;j++)
{
int dis=abs(M[i].x-H[j].x)+abs(M[i].y-H[j].y);
addedge(i,mcnt+j,dis,1);
//addedge(mcnt+j,i,dis,1);
}
}
src=0;
des=mcnt+hcnt+1;
for(i=1;i<=mcnt;i++)
addedge(src,i,0,1);
for(j=1;j<=hcnt;j++)
addedge(mcnt+j,des,0,1);
int ans=MCMF(src,des); printf("%d\n",ans);
}
return 0;
}

最小费用最大流模板 poj 2159 模板水题的更多相关文章

  1. 网络流(最小费用最大流):POJ 2135 Farm Tour

    Farm Tour Time Limit: 1000ms Memory Limit: 65536KB This problem will be judged on PKU. Original ID: ...

  2. 最小费用最大流(luogu P3381 【模板】最小费用最大流)

    题目链接 题目描述 如题,给出一个网络图,以及其源点和汇点,每条边已知其最大流量和单位流量费用,求出其网络最大流和在最大流情况下的最小费用. 输入输出格式 输入格式: 第一行包含四个正整数N.M.S. ...

  3. hdu 6437 /// 最小费用最大流 负花费 SPFA模板

    题目大意: 给定n,m,K,W 表示n个小时 m场电影(分为类型A.B) K个人 若某个人连续看了两场相同类型的电影则失去W 电影时间不能重叠 接下来给定m场电影的 s t w op 表示电影的 开始 ...

  4. SGU 185.Two shortest (最小费用最大流)

    时间限制:0.25s 空间限制:4M 题意: 在n(n<=400)个点的图中,找到并输出两条不想交的最短路.不存在输出“No sulotion”: Solution: 最小费用最大流 建图与po ...

  5. poj 2195 最小费用最大流模板

    /*Source Code Problem: 2195 User: HEU_daoguang Memory: 1172K Time: 94MS Language: G++ Result: Accept ...

  6. POJ 2135 Farm Tour (最小费用最大流模板)

    题目大意: 给你一个n个农场,有m条道路,起点是1号农场,终点是n号农场,现在要求从1走到n,再从n走到1,要求不走重复路径,求最短路径长度. 算法讨论: 最小费用最大流.我们可以这样建模:既然要求不 ...

  7. 最小费用最大流模板(POJ 2135-Farm Tour)

    最近正好需要用到最小费用最大流,所以网上就找了这方面的代码,动手写了写,先在博客里存一下~ 代码的题目是POJ2135-Farm Tour 需要了解算法思想的,可以参考下面一篇文章,个人觉得有最大流基 ...

  8. P3381 【模板】最小费用最大流

    P3381 [模板]最小费用最大流 题目描述 如题,给出一个网络图,以及其源点和汇点,每条边已知其最大流量和单位流量费用,求出其网络最大流和在最大流情况下的最小费用. 输入输出格式 输入格式: 第一行 ...

  9. Doctor NiGONiGO’s multi-core CPU(最小费用最大流模板)

    题目链接:http://acm.nyist.net/JudgeOnline/problem.php?pid=693 题意:有一个 k 核的处理器和 n 个工作,全部的工作都须要在一个核上处理一个单位的 ...

随机推荐

  1. hdu 5178 pairs (线性探查问题)

    Problem Description John has n points on the X axis, and their coordinates are (x[i],),(i=,,,…,n−). ...

  2. IOS 缩放图片常用方法

    /** * 指定Size压缩图片 (图片会压缩变形) * * @param image 原图 * @param size 压缩size * * @return 压缩后的图片 */ -(UIImage* ...

  3. HDOJ/HDU 2544 最短路---dijkstra算法

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2544 这题的思路可以见这里(同一类型):http://blog.csdn.net/xiaozhuaix ...

  4. Perl 多线程模块 Parallel::ForkManager

    Perl 多线程模块 Parallel::ForkManager 一个简单的并行处理模块.这个是用来对付循环的多线程处理. 放在循环前面. Table of Contents 1 Synops内容简介 ...

  5. AssemblyInfo.cs文件的作用

    在asp.net中有一个配置文件AssemblyInfo.cs主要用来设定生成的有关程序集的常规信息dll文件的一些參数,以下是默认的AssemblyInfo.cs文件的内容详细介绍 //是否符合公共 ...

  6. asp.net cookie和session的详细使用

    cookie使用代码: //设置Cookie HttpCookie setCookie = new HttpCookie("test"); setCookie.Values.Add ...

  7. 主运行循环main run loop的一些理解

    应用主运行循环负责处理所有用户相关的事件.UIApplication对象在应用启动时安装主运行循环并且使用此循环去处理事件和处理基于视图的界面更新.正如名字所表明的,该主运行循环是在应用的主线程app ...

  8. python-文件操作(1)

    本文内容涉及python打开/创建文件对象,文件的读写.文件指针位置的移动.获取命令行参数. 1. open() open函数以指定模式返回一个file对象,如: file_object = open ...

  9. Android开发环境的搭建之(一)Java开发环境的安装

    (1)  安装JDK(Java Developer Kit).下载JDK1.8并安装jdk-8u60-windows-i586.exe.下载官方链接http://www.oracle.com/tech ...

  10. OpenGL ES 2.0 变换

    基本变换都是通过将表示点坐标的向量与特定的变换矩阵相乘完成的. 进行基于矩阵的变换时,三位空间中点的位置需要表示成齐次坐标形式. 齐次坐标形式:在X.Y.Z3个坐标值后面增加第四个量W,未变换时W值一 ...