这题说的给了n个点m条边要求保证是一个有向无环图,可以删除至多k条边使得这个图的拓扑序的字典序最大,我们知道如果我们要排一个点的时候一定要考虑比他大的点是否可以、通过拆边马上拆出来,如果可以拆当然是拆,肯定保证字典序最大,如果不能拆,就不拆留着以后拆,当初这个比他大的点度数小于k的,最大是多少,这个方法我一直想不出,后来看了题解,二分加线段树,可以做到,线段树维护每个点的d[i],然后通过二分找出小于k的最大点是多少。

 #include <iostream>
#include <algorithm>
#include <string.h>
#include <vector>
#include <cstdio>
#include<queue>
using namespace std;
const int maxn =;
struct Edge{
int u,v;
Edge(int uu=, int vv=){
u= uu; v =vv;
}
};
vector<Edge> E;
vector<int> G[maxn],REG[maxn];
void add_edg(int u, int v){
E.push_back(Edge(u,v));
G[u].push_back(E.size()-);
REG[v].push_back(E.size()-);
}
int ind[maxn];
int cL, cR,cans;
struct Itree{
int id[maxn*];
void build(int O, int L, int R){
if(L==R){
id[O] = ind[L] ; return ;
}
int mid = ( L + R ) >> ;
build(O*,L,mid);
build(O*+,mid+,R);
id[O]=min(id[O*],id[O*+]);
}
void update(int o, int L, int R){
if( L == R ){
id[o] = cans; return ;
}
int mid=(L+R)>>;
if(cL<=mid){
update(o*,L,mid);
}else update(o*+,mid+,R);
id[o]=min(id[o*],id[o*+]);
}
void query(int o , int L, int R){
if(cL<=L && cR>=R){
cans =min(cans,id[o]);return ;
}
int mid = (L+R)>>;
if(cL <= mid) query(o*,L,mid);
if(cR>mid) query(o*+,mid+,R);
}
}T;
bool use[maxn];
void init(int n){
for(int i=; i<n; i++){
G[i].clear();
REG[i].clear();
}
E.clear();
memset(ind,,sizeof(ind));
memset(use,true,sizeof(use));
}
int jud(int k, int n){
int L=,R=n,ans=-;
while(L<=R){
int mid = (L+R)>>;
cans = k+;
cL=mid; cR=R;
T.query(,,n);
if(cans<=k){
ans=mid; L=mid+;
}
else R=mid-;
}
return ans;
}
priority_queue<int> Q;
void solve1(int nk,int k,int n){ for(int i=; i<REG[nk].size(); i++){
use[ REG[nk][i] ] = false;
}
cans = k+;
cL=cR=nk;
T.update(,,n);
}
void solve2(int nk,int k,int n){
for(int i=; i<G[nk].size(); i++){
int numedg = G[nk][i];
if(use[numedg]){
use[numedg]=false;
Edge q = E[numedg];
ind[q.v]--;
if(ind[q.v]==){
Q.push(q.v); ind[q.v]=k+;
}
cL = cR = q.v;
cans =ind[q.v];
T.update(,,n);
}
}
}
int ans[maxn];
int main()
{
int n,m,k; while(scanf("%d%d%d",&n,&m,&k)==){
init(n);
for(int i=; i<m; i++){
int u,v;
scanf("%d%d",&u,&v);
add_edg(u,v);
ind[v]++;
}
while(!Q.empty())Q.pop();
for(int i =; i<=n; i++){
if(ind[i]==){
Q.push(i);
ind[i]=k+;
}
}
T.build(,,n);
int st=;
while(!Q.empty()){
int top = Q.top();
int nk = jud(k,n);
if(nk>top){
k-=ind[nk];
solve1(nk,k,n);
Q.push(nk);
}else{
Q.pop();
ans[st++]=top;
solve2(top,k,n);
}
}
for(int i=; i<n-; i++) printf("%d ",ans[i]);
printf("%d\n",ans[n-]);
} return ;
}

hdu5195 二分+线段树+拓扑序的更多相关文章

  1. HDU4614 Vases and Flowers 二分+线段树

    分析:感觉一看就是二分+线段树,没啥好想的,唯一注意,当开始摆花时,注意和最多能放的比大小 #include<iostream> #include<cmath> #includ ...

  2. Tsinsen A1505. 树(张闻涛) 倍增LCA,可持久化线段树,DFS序

    题目:http://www.tsinsen.com/A1505 A1505. 树(张闻涛) 时间限制:1.0s   内存限制:512.0MB    总提交次数:196   AC次数:65   平均分: ...

  3. BZOJ_3252_攻略_线段树+dfs序

    BZOJ_3252_攻略_线段树+dfs序 Description 题目简述:树版[k取方格数] 众所周知,桂木桂马是攻略之神,开启攻略之神模式后,他可以同时攻略k部游戏.今天他得到了一款新游戏< ...

  4. 【XSY2534】【BZOJ4817】树点涂色 LCT 倍增 线段树 dfs序

    题目大意 ​ Bob有一棵\(n\)个点的有根树,其中\(1\)号点是根节点.Bob在每个点上涂了颜色,并且每个点上的颜色不同.定义一条路径的权值是:这条路径上的点(包括起点和终点)共有多少种不同的颜 ...

  5. J - Joseph and Tests Gym - 102020J (二分+线段树)

    题目链接:https://cn.vjudge.net/contest/283920#problem/J 题目大意:首先给你n个门的高度,然后q次询问,每一次询问包括两种操作,第一种操作是将当前的门的高 ...

  6. Educational Codeforces Round 61 D 二分 + 线段树

    https://codeforces.com/contest/1132/problem/D 二分 + 线段树(弃用结构体型线段树) 题意 有n台电脑,只有一个充电器,每台电脑一开始有a[i]电量,每秒 ...

  7. 【BZOJ-3110】K大数查询 整体二分 + 线段树

    3110: [Zjoi2013]K大数查询 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 6265  Solved: 2060[Submit][Sta ...

  8. hdu6070 Dirt Ratio 二分+线段树

    /** 题目:hdu6070 Dirt Ratio 链接:http://acm.hdu.edu.cn/showproblem.php?pid=6070 题意:给定n个数,求1.0*x/y最小是多少.x ...

  9. 【bzoj4817】树点涂色 LCT+线段树+dfs序

    Description Bob有一棵n个点的有根树,其中1号点是根节点.Bob在每个点上涂了颜色,并且每个点上的颜色不同.定义一条路 径的权值是:这条路径上的点(包括起点和终点)共有多少种不同的颜色. ...

随机推荐

  1. gitlab无法push或clone的错误:JWT::DecodeError (Nil JSON web token): lib/gitlab/workhorse.rb:120:in `verify_api_request!'

    使用源码安装的方式升级gitlib7.14到gitlab-8.13.5中文版,然后push的时候报错: 错误信息如下: Started GET "/gitlab/hushizhi/gitla ...

  2. [工具] Sublime Text 使用指南

    http://bbs.it-home.org/thread-46291-1-1.html 摘要(Abstract) 更新记录 更正打开控制台的快捷键为Ctrl + ` 更正全局替换的快捷键为Ctrl ...

  3. iOS interface适配

  4. Docker学习计划二:基本配置

    来源:http://www.ityouknow.com/docker/2018/03/07/docker-introduction.html Docker 将应用程序与该程序的依赖,打包在一个文件里面 ...

  5. Linguistic Data Consortium (LDC)

    搞NLP的人经常会听到一个神秘的名字LDC,因为大量的论文所使用的数据都来自于LDC,本文就来揭露其神秘面目. About LDC: LDC,全名Linguistic Data Consortium, ...

  6. git--指定不上传的文件夹

    在使用 vue-cli 脚手架的时候,有一个依赖模板文件夹是不希望被上传到git上的,因为里面文件太多了. 解决办法:手动创建git忽略push清单,node_module以及自身 1.文件夹内右键g ...

  7. sublime--将vue代码进行高亮显示

    vue的.vue文件sublime是不认识,但是为了让 .vue 文件看上去更加简洁:所以要用到一款不错的插件: 下载:vue-syntax-highlight https://gitee.com/m ...

  8. MatLab Mark Points 给点标序号

    在MatLab中,我们有时要给画出的点按一定顺序标上序号,下面这个简单的例子实现这个功能: x=rand(,); y=rand(,); plot(x,y,'r*'); text(x+:));

  9. Spyer中添加一些常用包的方法

    我用的是Anaconda中的Spyer编译,在导入包pyaudio时,发现找不到,需要手工导入.可以打开Anacoda promt,查看已经安装的包名用:pip list Spyer中的所有包在这里安 ...

  10. 浏览器指纹 - HTTP cookie 浏览器指纹 欺诈检测 浏览器id hash 浏览器插件信息 canvas 字体信息

    详解浏览器cookie和浏览隐私之间的关系http://www.iefans.net/cookie-yinsi-guanxi/ 详解浏览器cookie和浏览隐私之间的关系 浏览器相关 互联网 2013 ...