【网络流+贪心】Homework
题目描述
Taro is a student of Ibaraki College of Prominent Computing. In this semester, he takes two courses, mathematics and informatics. After each class, the teacher may assign homework. Taro may be given multiple assignments in a single class, and each assignment may have a different deadline. Each assignment has a unique ID number.
Everyday after school, Taro completes at most one assignment as follows. first, he decides which course’s homework to do at random by flipping a coin. Let S be the set of all the unfinished assignments of the chosen course whose deadline has not yet passed. If S is empty, he plays a video game without doing any homework on that day even if there are unfinished assignments of the other course. Otherwise, with T ⊆ S being the set of assignments with the nearest deadline among S, he completes the one with the smallest assignment ID among T.
The number of assignments Taro will complete until the end of the semester depends on the result of coin flips. Given the schedule of homework assignments, your task is to compute the maximum and the minimum numbers of assignments Taro will complete.
输入
The input consists of a single test case in the following format.
n m
s1 t1
.
.
.
sn tn
The first line contains two integers n and m satisfying 1 ≤ m < n ≤ 400. n denotes the total number of assignments in this semester, and m denotes the number of assignments of the mathematics course (so the number of assignments of the informatics course is n − m).
Each assignment has a unique ID from 1 to n; assignments with IDs 1 through m are those of the mathematics course, and the rest are of the informatics course. The next n lines show the schedule of assignments. The i-th line of them contains two integers si and ti satisfying 1 ≤ si ≤ ti ≤ 400, which means that the assignment of ID i is given to Taro on the si-th day of the semester, and its deadline is the end of the ti-th day.
输出
In the first line, print the maximum number of assignments Taro will complete. In the second line, print the minimum number of assignments Taro will complete.
样例输入
6 3
1 2
1 5
2 3
2 6
4 5
4 6
样例输出
6
2
不得不说,日本人的英语真难懂.
题意很简单,就是你有两项作业,一个是数学,一个是信息学,以及布置时间和结束时间。你每天就做一项,然后是抛硬币选作业。假如说你数学做完了,信息学作业还没写,但是天意告诉你要学数学,于是乎你打起了游戏。
- 完成的最多:
知道起始时间,用贪心做,先做快结束的。单调队列维护。 - 完成的最少:
就是这天你数学作业写完了,信息学作业还没写,但是天意告诉你要学数学。建图:跑网络流
sic->数学作业 f=1
数学作业->天 f=1
天->天 拆点 f=1
天->信息作业 f=1
信息作业->sink f=1
这就意味着如果这天你如果只有一项作业,那就不写
有两项 那就写一项。
- 为什么拆点? 这样就限制了一天只写一份作业。
#include<bits/stdc++.h>
using namespace std;
#define ll long long
const int maxn=1e5+7;
const int maxm=1e6+7;
int n,m,src,sink;
int head[maxn],tol=1,ans;
int cur[maxn],dep[maxn];
const int inf=0x3f3f3f3f;
struct Edge{int to,next,val;}e[maxm];
struct node{int s,t;}s[maxn];
void add(int u,int v,int f){
tol++;
e[tol].to=v;
e[tol].next=head[u];
e[tol].val=f;
head[u]=tol;
}
bool bfs(int s,int t){
queue<int>q;
memset(dep,-1,sizeof(dep));
q.push(s);
dep[s]=0;
while(!q.empty()){
int now=q.front();
q.pop();
for(int v,i=head[now];i;i=e[i].next){
v=e[i].to;
if(dep[v]==-1&&e[i].val){
dep[v]=dep[now]+1;
if(v==t) return true;
q.push(v);
}
}
}
return false;
}
int dfs(int x,int maxx){
if(x==sink) return maxx;
for(int& i=cur[x];i;i=e[i].next){
if(dep[e[i].to]==dep[x]+1&&e[i].val){
int flow=dfs(e[i].to,min(maxx,e[i].val));
if(flow){
e[i].val-=flow;
e[i^1].val+=flow;
return flow;
}
}
}
return 0;
}
void dinic(int s,int t){
ans=0;
while(bfs(s,t)){
for(int i=0;i<=t;i++) cur[i]=head[i];
while(int d=dfs(s,inf)) ans+=d;
}
}
bool cmp(node a,node b)
{
return a.s<b.s;
}
int main()
{
int n,math;
scanf("%d%d",&n,&math);
src=0;
sink=1201;
for(int i=1;i<=math;i++){
scanf("%d%d",&s[i].s,&s[i].t);
add(src,i,1);
add(i,src,0);
for(int j=s[i].s;j<=s[i].t;j++){
add(i,j+400,1);
add(j+400,i,0);
}
}
for(int i=1;i<=400;i++){
add(i+400,i+800,1);
add(i+800,i+400,0);
}
for(int i=math+1;i<=n;i++){
scanf("%d%d",&s[i].s,&s[i].t);
add(i,sink,1);
add(sink,i,0);
for(int j=s[i].s;j<=s[i].t;j++){
add(j+800,i,1);
add(i,j+800,0);
}
}
priority_queue<int, vector<int>, greater<int> > Q;
sort(s+1,s+n+1,cmp);
int now=1,ans1=0;
for(int i=1;i<=400;i++){
while(now<=n&&i==s[now].s) {Q.push(s[now].t);now++;}
if(!Q.empty()&&i<=Q.top()){Q.pop();ans1++;}
while(!Q.empty()&&i>=Q.top()){Q.pop();}
}
dinic(src,sink);
printf("%d\n",ans1);
printf("%d\n",ans);
return 0;
}
【网络流+贪心】Homework的更多相关文章
- 洛谷P1251 餐巾(网络流)
P1251 餐巾 15通过 95提交 题目提供者该用户不存在 标签网络流贪心 难度提高+/省选- 提交该题 讨论 题解 记录 最新讨论 为什么我全部10个测试点都对… 题目描述 一个餐厅在相继的N天里 ...
- woj1008feedinganimals2-贪心-网络流
title: woj1008feedinganimals2-贪心-网络流 date: 2020-03-07 categories: acm tags: [acm,woj,网络流,贪心] 中等题. 标准 ...
- bzoj3661
网络流/贪心 网络流做法是对于每一列,如果一个兔子下一天继续可以存在,那么连一条容量为1的边,然后设立一个中转站,来控制可以换的数量,容量限制l.时限100s,能跑过去我的太慢了,一个点100s 正解 ...
- HDU 1789 Doing Homework again(贪心)
Doing Homework again 这只是一道简单的贪心,但想不到的话,真的好难,我就想不到,最后还是看的题解 [题目链接]Doing Homework again [题目类型]贪心 & ...
- 【CodeForces 589F】Gourmet and Banquet(二分+贪心或网络流)
F. Gourmet and Banquet time limit per test 2 seconds memory limit per test 512 megabytes input stand ...
- HDU 1789 Doing Homework again(贪心)
在我上一篇说到的,就是这个,贪心的做法,对比一下就能发现,另一个的扣分会累加而且最后一定是把所有的作业都做了,而这个扣分是一次性的,所以应该是舍弃扣分小的,所以结构体排序后,往前选择一个损失最小的方案 ...
- hdu--1798--Doing Homework again(贪心)
Doing Homework again Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Oth ...
- ACM-ICPC 2018 沈阳赛区网络预赛 F Fantastic Graph(贪心或有源汇上下界网络流)
https://nanti.jisuanke.com/t/31447 题意 一个二分图,左边N个点,右边M个点,中间K条边,问你是否可以删掉边使得所有点的度数在[L,R]之间 分析 最大流不太会.. ...
- 【BZOJ3716】[PA2014]Muzeum(贪心,网络流)
[BZOJ3716][PA2014]Muzeum(贪心,网络流) 题面 BZOJ 题解 很明显可以写最大权闭合子图,然后会\(TLE\)成傻逼. 为了方便,就把一个警卫能够看到的范围处理一下(把坐标系 ...
随机推荐
- Shiro密码处理
散列算法一般用于生成数据的摘要信息,是一种不可逆的算法,一般适合存储密码之类的数据,常见的散列算法如 MD5.SHA等.一般进行散列时最好提供一个 salt(盐),比如加密密码"admin& ...
- CF_448D 二分
给定n m k n和m为一个矩阵的行和列,都从1开始,矩阵的每个元素的值即为 i*j(行*列),求里面第k个数 还想找什么规律,发现虽然矩阵里面很有规律,但是n 和m在不断变化 根本不好找 其实元素从 ...
- consul集群配置
consul agent -server -bootstrap-expect 1 -data-dir /etc/consul -node=consul1 -bind=ip1 -ui -client=0 ...
- python从命令窗口启动脚本 创建并写入内容到文件示例
写入到文件示例: #!/usr/bin/env python3 from math import exp, log, sqrt import re from datetime import date, ...
- cf1228 D Complete Tripartite(哈希)
题意: 无向简单图,无自环,无重边,n个点,m条边,请你将这n个点分为3个互相没有交集的集合.并且满足以下条件: 1.同一个集合中的任意两点之间没有边. 2.每个点都要与除了它这个集合以外的所有点相连 ...
- LeetCode做题笔记之动态规划
LeetCode之动态规划 时间有限只做了下面这几道:70.338.877.96.120.95.647,后续会继续更新 70:爬楼梯 先来道简单的练练手,一道经典的动态规划题目 可以采用动态规划的备忘 ...
- C++逐行读取txt
C++读取txt文件的时候可以使用std::ifstream来实现,如果打开文件失败的话,其变量会是空的,所以可以用来判断是否打开成功. #include <stdlib.h> #in ...
- PHP+InfiniteScroll实现网页无限滚动加载数据实例
PHP+InfiniteScroll实现网页无限滚动加载数据实例,实现原理:当滚动条到底离网页底部一定长度的时候,向后台发送页数并获取数据. 首先我们在页面上先放置10条数据,即第一页,每一项都是p标 ...
- 寒假day15
今天完成了毕设的人才动态模块,同时刷了计算机网络的相关面试题
- MySQL--SQL分类
SQL语句主要可以划分为以下3个类别: DDL(Data Definition Languages)语句:数据定义语言,这些语句定义了不同的数据段.数据库.表.列.索引等数据库对象. 常用的语句关键字 ...