洛谷P4382 劈配
不知道这个Zayid是谁...
题意:
有n个人,m个导师。每个导师能接纳bi个人,每个人对于这m个导师都有一个志愿档次。
优先满足靠前的人,问到最后每个人匹配的导师是他的第几志愿。
每个人又有一个限制si,问至少前进多少名才能被志愿档次不大于si的导师录取。
解:
首先发现,每个志愿档次只能填一个人的时候,可以直接贪心。否则在同一志愿档次内选择不同的导师会对后面有影响。
这时我们就可以利用网络流。
一个流量代表一个的归属,动态加边。
对于每个人枚举志愿档次,添加流向导师的边。然后看是否有流量。
如果有流量那么他就归于该志愿档次。
第二问,答案可以二分。
很简朴的想法是对于每个二分出来的值,重新建图来一遍。这样复杂度就是Tnlogn * nm,显然不行。
发现每次重新建图的时候我们进行了很多一模一样的操作。于是考虑把前k个人的网络流状态保存下来,之后直接调用。
但是太麻烦了...我们又发现一种很巧妙的方法:判断在前k个人加完之后是否可行,其实是看哪些导师还可以接纳人。于是我们从汇点出发,反向DFS,能够得到每次从哪些导师出发有增广路,就是哪些导师还能接纳。
然后二分的时候直接O(m)判定。
这样我们发现有90分,超时一个点。
回想第一问网络流的时候,如果一个志愿档次没有流量,那么这些加的边就没有用,不妨删了。
然后就A了...
#include <queue>
#include <cstdio>
#include <vector>
#include <cstring>
#include <algorithm> const int N = , INF = 0x3f3f3f3f; int b[N], C, n, m, a[N][N], s[N], mat[N];
std::vector<int> topo[N][N]; namespace fl { struct Edge {
int nex, v, c;
}edge[]; int top = ; int d[N << ], e[N << ], E[N << ], TOP;
bool vis[N][N << ];
std::queue<int> Q; inline void add(int x, int y, int z) {
top++;
edge[top].v = y;
edge[top].c = z;
edge[top].nex = e[x];
e[x] = top; top++;
edge[top].v = x;
edge[top].c = ;
edge[top].nex = e[y];
e[y] = top;
return;
} inline bool BFS(int s, int t) {
memset(d, , sizeof(d));
d[s] = ;
Q.push(s);
while(!Q.empty()) {
int x = Q.front();
Q.pop();
for(int i = e[x]; i; i = edge[i].nex) {
int y = edge[i].v;
if(!edge[i].c || d[y]) {
continue;
}
d[y] = d[x] + ;
Q.push(y);
}
}
return d[t];
} int DFS(int x, int t, int maxF) {
if(x == t) {
return maxF;
}
int Ans = ;
for(int i = e[x]; i; i = edge[i].nex) {
int y = edge[i].v;
if(!edge[i].c || d[x] + != d[y]) {
continue;
}
int temp = DFS(y, t, std::min(edge[i].c, maxF - Ans));
if(!temp) {
d[y] = INF;
}
Ans += temp;
edge[i].c -= temp;
edge[i ^ ].c += temp;
if(Ans == maxF) {
break;
}
}
return Ans;
} inline int dinic(int s, int t) {
int Ans = ;
while(BFS(s, t)) {
Ans += DFS(s, t, INF);
}
return Ans;
} void DFS(int x, int k) {
vis[k][x] = ;
for(int i = e[x]; i; i = edge[i].nex) {
int y = edge[i].v;
if(!edge[i ^ ].c || vis[k][y]) {
continue;
}
DFS(y, k);
}
return;
} inline bool check(int x, int mid) {
for(int k = ; k <= s[x]; k++) {
for(int jj = topo[x][k].size() - ; jj >= ; jj--) {
int j = topo[x][k][jj];
if(vis[x - mid - ][j + n]) {
return ;
}
}
}
return ;
} inline void solve() {
memset(vis[], -, sizeof(vis[]));
int S = n + m + , T = n + m + ;
for(int i = ; i <= m; i++) {
add(n + i, T, b[i]);
}
for(int i = ; i <= n; i++) {
add(S, i, );
mat[i] = ;
for(int k = ; k <= m; k++) {
TOP = top;
E[i] = e[i];
for(int jj = topo[i][k].size() - ; jj >= ; jj--) {
int j = topo[i][k][jj];
E[n + j] = e[n + j];
add(i, n + j, );
}
int temp = dinic(S, T);
if(temp) {
mat[i] = k;
break;
}
else {
e[i] = E[i];
for(int jj = topo[i][k].size() - ; jj >= ; jj--) {
int j = topo[i][k][jj];
e[n + j] = E[n + j];
}
top = TOP;
}
}
if(!mat[i]) {
mat[i] = m + ;
}
DFS(T, i);
}
for(int i = ; i <= n; i++) {
printf("%d ", mat[i]);
}
puts("");
// first OVER for(int i = ; i <= n; i++) {
if(mat[i] <= s[i]) {
printf("0 ");
continue;
}
int l = , r = i;
while(l < r) {
int mid = (l + r) >> ;
if(check(i, mid)) {
r = mid;
}
else {
l = mid + ;
}
}
printf("%d ", r);
}
puts("");
return;
} inline void clear() {
memset(e, , sizeof(e));
top = ;
memset(vis, , sizeof(vis));
return;
}
} inline void solve() {
scanf("%d%d", &n, &m);
for(int i = ; i <= m; i++) {
scanf("%d", &b[i]);
}
for(int i = ; i <= n; i++) {
for(int j = ; j <= m; j++) {
scanf("%d", &a[i][j]);
if(a[i][j]) {
topo[i][a[i][j]].push_back(j);
}
}
}
for(int i = ; i <= n; i++) {
scanf("%d", &s[i]);
}
// read over fl::solve();
return;
} inline void clear() {
for(int i = ; i <= n; i++) {
for(int j = ; j <= m; j++) {
topo[i][j].clear();
}
}
fl::clear();
return;
} int main() { int T;
scanf("%d%d", &T, &C);
while(T--) {
solve();
if(T) {
clear();
}
}
return ;
}
AC代码
我发现D2T1都好毒瘤...屠龙勇士也是的。
洛谷P4382 劈配的更多相关文章
- 洛谷P4382 [八省联考2018]劈配(网络流,二分答案)
洛谷题目传送门 说不定比官方sol里的某理论最优算法还优秀一点? 所以\(n,m\)说不定可以出到\(1000\)? 无所谓啦,反正是个得分题.Orz良心出题人,暴力有70分2333 思路分析 正解的 ...
- 洛谷P5289 皮配
解:观察一波部分分. 首先小数据直接暴力4n,然后考虑背包.设f[i][a][b][c]表示前i个学校中前三位导师分别有多少人,第四位导师可以直接推出来. 然后暴力枚举每一个人放在哪进行背包. 进一步 ...
- 【BZOJ5251】【八省联考2018】劈配(网络流,二分答案)
[BZOJ5251][八省联考2018]劈配(网络流,二分答案) 题面 洛谷 BZOJ Description 一年一度的综艺节目<中国新代码>又开始了. Zayid从小就梦想成为一名程序 ...
- [洛谷P3643] [APIO2016]划艇
洛谷题目链接:[APIO2016]划艇 题目描述 在首尔城中,汉江横贯东西.在汉江的北岸,从西向东星星点点地分布着 \(N\) 个划艇学校,编号依次为 \(1\) 到 \(N\).每个学校都拥有若干艘 ...
- 洛谷P1991 无线通讯网
P1991 无线通讯网 170通过 539提交 题目提供者洛谷OnlineJudge 标签图论 难度普及+/提高 提交该题 讨论 题解 记录 最新讨论 怎么又炸了 为啥一直40!求解! UKE:inv ...
- BZOJ5251:[九省联考2018]劈配——题解
https://www.lydsy.com/JudgeOnline/problem.php?id=5251 https://loj.ac/problem/2477 <-可以看数据 https: ...
- COCI2017-2018#3 Dojave || 洛谷P4443
题目传送门............................................................................................... ...
- 【洛谷4933】大师(DP)
题目: 洛谷4933 分析: (自己瞎yy的DP方程竟然1A了,写篇博客庆祝一下) (以及特斯拉电塔是向Red Alert致敬吗233) 这里只讨论公差不小于\(0\)的情况,小于\(0\)的情况进行 ...
- 洛谷P2507 [SCOI2008]配对 题解(dp+贪心)
洛谷P2507 [SCOI2008]配对 题解(dp+贪心) 标签:题解 阅读体验:https://zybuluo.com/Junlier/note/1299251 链接题目地址:洛谷P2507 [S ...
随机推荐
- 【文章存档】Azure Web 应用如何修改 IIS 配置
链接 https://docs.azure.cn/zh-cn/articles/azure-operations-guide/app-service-web/aog-app-service-web-h ...
- centos7.6 安装配置rabbitmq
IP地址:192.168.200.108 安装erlang 和 依赖环境 yum install -y socat yum install -y erlang 安装rabbitmq yum insta ...
- Tomcat ngxin 反向代理
tomcat nginx 反向代理 安装nginx yum直接安装 yum install nginx –y 也可以编译安装 这是用编译安装,新手可以用yum安装 配置文件在 /etc/nginx/c ...
- pkill命令详解
基础命令学习目录首页 原文链接:http://www.mamicode.com/info-detail-2315063.html 一:含义: 是ps命令和kill命令的结合,按照进程名来杀死指定进程, ...
- React的setState分析
前端框架层出不穷,不过万变不离其宗,就是从MVC过渡到MVVM.从数据映射到DOM,angular中用的是watcher对象,vue是观察者模式,react就是state了. React通过管理状态实 ...
- second scrum meeting - 151026
摘要:这一周的工作其实进行的并没有很迅速~不过我们团队的每个人都在慢慢进行自己的工作,并且我们也完成了大致的页面设计,开发了主页面的框架,并且我们也会开始着手学习服务器的操作,还有更加完善主页面的框架 ...
- OO学习体会与阶段总结(设计与实现)
前言 在最近的一个月的课程中,笔者对于规格化编程进行了深入的学习.运用面向对象抽象思想对编写的程序进行过程抽象.异常处理.数据抽象.类的层次规格与迭代等等规格设计,使得程序结构化程度提高,具有更好 ...
- Java文件写入时是否覆盖
这个是和服务器读数据结合着来的,是向服务器文件写数据,这就碰到了是否覆盖以前写的数据的问题,看FileWriter();的参数后面的参数名叫append,用词典查是附加的意思,灵机一动,改成false ...
- 浅谈对IT的认识!
我是一个从农村出来的学生,家里的情况和大多数的农村同学是一样的,家里算不上有钱,父母供我读书,也已经是做到仁至义尽了. 我现在选了,一个和计算机有关的专业---计算机应用技术.就是希望毕业后,可以找到 ...
- Leetcode题库——34.在排序数组中国查找元素的第一个和最后一个位置
@author: ZZQ @software: PyCharm @file: searchRange.py @time: 2018/11/12 19:19 要求:给定一个按照升序排列的整数数组 num ...