[CF538H]Summer Dichotomy
[CF538H]Summer Dichotomy
题目大意:
将若干个学生分为两个班级\(S_1,S_2\),每个班的学生数分别为\(n_1,n_2\)(甚至可以没有学生,也可以没有老师)。给出限制\(t_{\min},t_{\max}\),要求\(t_{\min}\le n_1+n_2\le t_{\max}\)。有\(n(n\le10^5)\)个老师,每个老师希望他所任教的班级人数在\([l_i,r_i]\)范围内。有\(m(m\le10^5)\)对老师之间有一些私人恩怨,不能分在一个班级。问是否存在合法的分班方案。如果有,求出其中的任意一种,输出每个班的总人数以及各个老师所任教的班级。
思路:
对于所有\([l_i,r_i]\)的限制,我们不妨假设\(n_1=\min\{r_i\},n_2=\max\{l_i\}\),显然这是比较松的约束。再考虑\(t_{\min},t_{\max}\)的限制,确定可行的一组\(n_1,n_2\)。考虑二分图染色构造老师分配的方案。对于只能分到\(S_1\)或只能分到\(S_2\)的老师DFS遍历染色,若更新到的结点与已染色结点矛盾,说明根本不是二分图,不存在合法的方案。对于两个都不可以分进去的,说明也不存在合法方案。最后再对于\(S_1\)和\(S_2\)都可以的进行染色。
源代码:
#include<cstdio>
#include<cctype>
#include<vector>
#include<climits>
inline int getint() {register char ch;while(!isdigit(ch=getchar()));register int x=ch^'0';while(isdigit(ch=getchar())) x=(((x<<2)+x)<<1)+(ch^'0');return x;
}
constexpr int N=1e5;
int l[N],r[N],ans[N];
std::vector<int> e[N];
inline void add_edge(const int &u,const int &v) {e[u].push_back(v);e[v].push_back(u);
}
void dfs(const int &x,const int &c) {if(ans[x]) {if(ans[x]!=c) throw(0);return;}ans[x]=c;for(auto &y:e[x]) {dfs(y,3-c);}
}
int main() {const int t_min=getint(),t_max=getint();const int n=getint(),m=getint();int n1=INT_MAX,n2=INT_MIN;for(register int i=0;i<n;i++) {n2=std::max(n2,l[i]=getint());n1=std::min(n1,r[i]=getint());}if(n1+n2<t_min) n2=t_min-n1;else if(n1+n2>t_max) n1=t_max-n2;if(n1<0||n2<0) {puts("IMPOSSIBLE");return 0;}for(register int i=0;i<m;i++) {add_edge(getint()-1,getint()-1);}for(register int i=0;i<n;i++) {try {if(!(l[i]<=n1&&n1<=r[i])&&!(l[i]<=n2&&n2<=r[i])) throw(0);if((l[i]<=n1&&n1<=r[i])&&!(l[i]<=n2&&n2<=r[i])) dfs(i,1);if((l[i]<=n2&&n2<=r[i])&&!(l[i]<=n1&&n1<=r[i])) dfs(i,2);} catch(...) {puts("IMPOSSIBLE");return 0;}}for(register int i=0;i<n;i++) {try {if(!ans[i]) dfs(i,1);} catch(...) {puts("IMPOSSIBLE");return 0;}}puts("POSSIBLE");printf("%d %d\n",n1,n2);for(register int i=0;i<n;i++) {printf("%d",ans[i]);}return 0;
}
转载于:https://www.cnblogs.com/skylee03/p/9084408.html
[CF538H]Summer Dichotomy相关推荐
- CF538H Summer Dichotomy
题意:可以录取x个学生,t<=x<=T.将学生分成两组,大小分别为n1,n2.一共有n个老师需要分进这两个组里,有m对老师互相讨厌不能同组,每个老师都对其所在组的大小有[li,ri]的限制 ...
- 训练3.21(C:Summer Dichotomy)
训练3.21(C:Summer Dichotomy) cf538H 题目:http://code**forces.com/problemset/problem/538/H 题意:T个学生来报考,至少录 ...
- Definition of Dichotomy
台大的线上课程,Machine Learning Foundations,对于Dichotomy的定义: 大家对此定义,是否感到困惑?式子左边有h,为何右边也有h? 这有点像是我们在念文言文,有许多字 ...
- 数据结构之Python实现二分法查找dichotomy
""" 定义一个数组780 从里面查89 """def dichotomy(list, item):low = 0high = len(li ...
- 二分法查找(dichotomy)--python实现
二分法原理及实现 二分法原理概述 python实现代码 二分法原理概述 简单粗暴一点理解二分法 将数据有序排列:先将一个数据集进行有序排列(可根据某种数值的大小降序或升序<当然排序的规则可根据业 ...
- Dichotomy二分法学习笔记
二分法 二分法的特点 依赖于递归算法,逐次将区间长度减半,直至无限逼近所求点的方法. 算法的复杂度与区间长度,精度,待求点的位置分布有关 LeetCode 69 实现 int sqrt(int x) ...
- 【Codeforces 538 H】Summer Dichotomy(二分图染色)
传送门 显然是不能在一起的连边后二分图染色 似乎可以直接用setsetset维护一下可行的点染色 不过更简单的是 如果有三个[li,ri][l_i,r_i][li,ri]互相不交显然无解 可以得到 ...
- Dichotomy(递+非递)
输入:先输入进行二分搜索元素的个数,然后按大小依次输入(或随机生成,然后排序)每个数字,最后输入要求搜索的元素. 输出:要求搜索元素的下标(下标从0开始!). 示例:输入:61 5 5 9 6 9 6 ...
- Dichotomy专栏:Leetcode:#33 搜索旋转排序数组
Question: 整数数组 nums 按升序排列,数组中的值 互不相同 . 在传递给函数之前,nums 在预先未知的某个下标 k(0 <= k < nums.length)上进行了 旋转 ...
最新文章
- 微信小程序图片上传到服务器再自动替换,微信小程序批量上传图片到服务器,并实现预览,删除功能...
- 机器人流程自动化(RPA)系统原理及特点
- DOM对象与 JQuery对象互相转化
- python项目实例初学者-经典Python案例,初学者的小帮手,立马学会Python!
- UCINET 社会网络分析工具
- java中的exception stack有时候不输出的原因
- 用定时器控制灯的闪烁梯形图_用西门子PLC设计灯的闪烁的梯形图,就只要梯形图。...
- Druid:数据库连接池实现技术,由阿里巴巴提供的
- 飘逸的python - yield简明教程
- 微信小程序使用字体图标库
- pdf 分形 张济忠_分形
- mouseenter和mouseleave与mouseover和mouseout的区别
- 第3.1~3.3节《合成孔径雷达成像原理-皮亦鸣》
- 彻底卸载vscode Linux,Ubuntu vscode 安装与卸载
- Python爬虫从入门到精通:(6)数据解析2_使用bs4(BeautifulSoup)_Python涛哥
- 实施360绩效评估的的3个关键事项
- 牛客网 OI 赛制测试赛
- ubuntu安装android应用程序,Anbox将使Ubuntu手机能运行Android应用程序
- Spring框架的自动装配
- C语言编写的坦克大战exe小游戏