【BZOJ】1070: [SCOI2007]修车
1070: [SCOI2007]修车
Description
同 一时刻有N位车主带着他们的爱车来到了汽车维修中心。维修中心共有M位技术人员,不同的技术人员对不同的车进行维修所用的时间是不同的。现在需要安排这M 位技术人员所维修的车及顺序,使得顾客平均等待的时间最小。 说明:顾客的等待时间是指从他把车送至维修中心到维修完毕所用的时间。
Input
第一行有两个m,n,表示技术人员数与顾客数。 接下来n行,每行m个整数。第i+1行第j个数表示第j位技术人员维修第i辆车需要用的时间T。
Output
最小平均等待时间,答案精确到小数点后2位。
Sample Input
3 2
1 4
Sample Output
HINT
数据范围: (2<=M<=9,1<=N<=60), (1<=T<=1000)
思路:开始以为排序之后模拟贪心,但是车的数量太多...每次对于一个工人来说,并不是直接按照他修理车的最短时间给他分配车的,还要看里面各种..修车时间差与等待总时间等因素;所以要用到网络流构图,让计算机不断的调整选择方案(增广路模拟);即最小费用最大流问题;
暴力构图:每个工人可能修理的车的数量即为车的数量,并且每次修理车的时间并不只是输入的时间,因为对于同一个工人来说其前面修理的车的时间会累加到后面修车的时间里面;但是一般这样前面对后面产生的次数影响,并不是对当前的车去看它前面修了哪些车,然后把这些车的总时间加上自己的时间代价的,因为这样还要不断记录与修改修车的顺序。。与其后面每次来找前面的麻烦。。还不如前面修理的时候直接计算出对后面的影响~~ 即该车是同一个工人倒数第k次修的,那么这辆车的总代价就是k*time[i][j];这样就有了暴力拆点的依据了~~
暴力拆点:把每个工人拆成m个点,第k个点表示是倒数第k次修的该车,至于该车就修改每辆车与n*m个点连边,边的容量为1,表示只修一次。费用为time[i]][j]*k;至于与超级源点和汇点连边时,cap为1,但是费用记得要记为0;这样直接跑最大流即可;
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
using namespace std;
#define MS0(a) memset((a),0,sizeof(a))
#define MSi(a) memset((a),0x3f,sizeof(a))
#define MS1(a) memset((a),-1,sizeof(a))
#define inf 0x3f3f3f3f
const int T = ;
const int M = ;
const int N = ;
int tot = ,head[N];
struct edge{
int from,to,Next,cap,cost;
}e[M<<];
void ins(int u,int v,int cap,int cost)
{
e[++tot].Next = head[u];// tot从2开始,之后增广边还是可以异或~~并且head并不需要设为-1.
e[tot].from = u, e[tot].to = v;
e[tot].cap = cap; e[tot].cost = cost;
head[u] = tot;
}
void insert(int u,int v,int cap,int cost)//把cap当成费用;之后增广路中只是改变flow;
{
ins(u,v,cap,cost);ins(v,u,,-cost);
}
int t[][],dis[N],vis[N],p[N];
queue<int> que;
int spfa()
{
MSi(dis);
que.push();
p[] = ;dis[] = ;
while(!que.empty()){
int u = que.front();que.pop();
vis[u] = ;
for(int d = head[u];d ;d = e[d].Next){
int v = e[d].to;
if(e[d].cap && dis[v] > dis[u] + e[d].cost){
dis[v] = dis[u]+e[d].cost;
p[v] = d;
if(!vis[v]){
que.push(v);
vis[v] = ;
}
}
}
}
if(dis[T] == inf) return ;
return ;
}
int ans;
int mcf()
{
int v = inf;
for(int d = p[T];d;d = p[e[d].from])
v = min(v,e[d].cap);
for(int d = p[T];d;d = p[e[d].from]){
e[d].cap -= v; e[d^].cap += v;
ans += e[d].cost;
}
}
int main()
{
int n,m;
scanf("%d%d",&n,&m);
for(int i = ;i <= m;i++)
for(int j = ;j <= n;j++)
scanf("%d",&t[i][j]);
for(int i = ;i <= n;i++)
for(int j = ;j <= m;j++)
insert(,(i-)*m+j,,);
for(int i = n*m+;i <= n*m+m;i++)
insert(i,T,,);
for(int i = ;i <= n;i++)
for(int j = ;j <= m;j++)//第i个工人修的倒数第j辆车;
for(int k = ;k <= m;k++)
insert((i-)*m+j,n*m+k,,t[k][i]*j);
while(spfa()) mcf();
printf("%.2f",.*ans/m);
}
【BZOJ】1070: [SCOI2007]修车的更多相关文章
- BZOJ 1070: [SCOI2007]修车 [最小费用最大流]
1070: [SCOI2007]修车 Time Limit: 1 Sec Memory Limit: 128 MBSubmit: 4936 Solved: 2032[Submit][Status] ...
- bzoj 1070: [SCOI2007]修车 费用流
1070: [SCOI2007]修车 Time Limit: 1 Sec Memory Limit: 162 MBSubmit: 2785 Solved: 1110[Submit][Status] ...
- bzoj 1070 [SCOI2007]修车(最小费用最大流)
1070: [SCOI2007]修车 Time Limit: 1 Sec Memory Limit: 162 MBSubmit: 3515 Solved: 1411[Submit][Status] ...
- [BZOJ 1070] [SCOI2007] 修车 【费用流】
题目链接:BZOJ - 1070 题目分析 首先想到拆点,把每个技术人员拆成 n 个点,从某个技术人员拆出的第 i 个点,向某辆车连边,表示这是这个技术人员修的倒数第 i 辆车.那么这一次修车对整个答 ...
- BZOJ 1070: [SCOI2007]修车(费用流)
http://www.lydsy.com/JudgeOnline/problem.php?id=1070 题意: 思路: 神奇的构图. 因为排在后面的人需要等待前面的车修好,这里将每个技术人员拆成n个 ...
- bzoj 1070 [SCOI2007]修车——网络流(拆边)
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1070 后面还有几辆车在这个人这儿修,自己这辆车的时间对总时间的贡献就要多乘上几倍. 所以可以 ...
- bzoj 1070 [SCOI2007]修车
最小费用最大流. 将每个技术人员拆成车数个点,技术人员i的第j个点代表技术人员i修的倒数第j辆车. 源点向所有技术人员点连一条容量为1费用为0的边. 所有技术人员点向所有车点连边:技术人员i的第j个点 ...
- BZOJ.1070.[SCOI2007]修车(费用流SPFA)
题目链接 /* 神tm看错题*2.. 假如人员i依次维修W1,W2,...,Wn,那么花费的时间是 W1 + W1+W2 + W1+W2+W3... = W1*n + W2*(n-1) + ... + ...
- 【刷题】BZOJ 1070 [SCOI2007]修车
Description 同一时刻有N位车主带着他们的爱车来到了汽车维修中心.维修中心共有M位技术人员,不同的技术人员对不同的车进行维修所用的时间是不同的.现在需要安排这M位技术人员所维修的车及顺序,使 ...
- bzoj 1070: [SCOI2007]修车【最小费用最大流】
一开始从客人角度想的,怎么建都不对 从一个修车工所接待的所有顾客花费的总时间来看,设一共有x个人,那么第一个修的对总时间的贡献是x*w1,第二个是(x-1)*w2-以此类推.所以把第i个修车工拆成n组 ...
随机推荐
- mkfs.xfs命令没找到
yum install xfsprogs xfsdump
- 关于JFace的自定义对话框(Dialog类)
仅仅是使用MessageDialog,InputDialog等JFace中现成的对话框类是无法满足实际项目开发需要的. 很多时候都需要自己定制对话框,自定义对话框只要在Dialog类的基础上作扩展就行 ...
- 怎样安装WIN7系统
如何避免win7自动创建200M隐藏分区 1 安装win7到选择安装到哪个分区的时候,不能选择 unallocated diskspace ,也不能选 delete 已有的分区(例如C盘)安全的做法是 ...
- Ajax效果
Ajax的效果就是不通过网页的跳转,就可以通过请求,就可以自动加载某个网页,在注册帐号时,经常 不通过网页跳转从数据库中查看是否有相同数据的出现,确认是否能够正确注册 下面是用其他方式实现ajax的效 ...
- Mongodb集群节点故障恢复场景分析
http://blog.csdn.net/zhangzhaokun/article/details/6299527 一个适当配置的Mongodb分片集群是没有单点故障. 本文描述了分片集群中存在的几种 ...
- C#学习笔记5:数据类型与进制转换
1.C#: 8种整形类型.2种用于科学计算的二进制浮点类型.1种用于金融计算的十进制浮点类型. 2.Decimal是一种特殊的浮点类型,能够存储大数字而无表示错误. 常用于货币计算.在表示的所有十进制 ...
- .net 邮件批量发送功能源码
#define debug using System; using System.Text; using System.Linq; using System.IO; using System.Ne ...
- Meteor错误:TypeError: Meteor.userId is not a function
问题描述: 浏览器console提示错误TypeError: Meteor.userId is not a function. 原因分析: 通过查看Meteor API文档,可知该函数由包accoun ...
- WEB系统技术开发方向
1. UI框架:要可以结合jquery+自定义服务器控件开发一套UI框架: 2.WEB报表设计器:用js开发一套可以自定义报表设计器: 3.WEB自定义表单+工作流设计器: 4.WEB打印组件: 5. ...
- string[] 和 arraylist互转及问题解决
1,String 数组转成 list<String> String[] s={"1","2","3","5" ...