一开始,没想出来,先topsort判环,把impossible拿到手,然后划分联通块,对每个联通块跑一遍topsort,觉得可对了,然后被大样例教育明白了,知道自己的策略错在哪了。

接着在纸上疯狂手模样例,不停地换topsort的顺序和贪心的方法,然后发现一种可行的解法。

开大根堆,对反图跑topsort,然后倒序输出。

这是一种贪心的策略,通过上述操作,我们可以使不但大,而且限制多的不优秀点在最后输出,而小而且限制少的在前输出,既不违反规则,字典序又最小。

换另一种解释,题目要我们输出满足拓扑序的最小字典序,是两个可能矛盾的量,他们之间可能存在冲突,那我们就倒着来,找满足拓扑逆序的最大字典序,这两个量都可以否定一个数字出现在靠前位置,把它们先找出来,然后倒着输出,就可以了。

其实上述过程只用一个topsort就搞定了,但是博主略懒,以前的那个top判环没删,就直接用了,导致时间略长。大家还是自己去打打吧,就当复习topsort了。

#include<iostream>
#include<algorithm>
#include<cmath>
#include<cstdio>
#include<cstring>
#include<vector>
#include<map>
#include<set>
#include<queue>
#include<stack>
using namespace std;
int read(){
int sum=,f=;char x=getchar();
while(x<''||x>''){
if(x=='-') f=-;
x=getchar();
}while(x>=''&&x<=''){
sum=sum*+x-'';
x=getchar();
}return sum*f;
}
int T,n,m,du[],pos[],ans[],size[],du1[],cnt;
vector<int>edge[];
vector<int>lcc[];
vector<int>e[];
bool v[];
map<pair<int,int>,bool>mp[];
bool check(){
bool vis[];
memset(vis,,sizeof(vis));
queue<int>tops;
while(!tops.empty())
tops.pop();
for(int i=;i<=n;i++)
if(du[i]==){
tops.push(i);
vis[i]=;
// cout<<i<<" ";
}
while(!tops.empty()){
int x=tops.front();
tops.pop();
for(int i=;i<edge[x].size();i++){
int y=edge[x][i];
du[y]--;
if(du[y]==){
tops.push(y);
vis[y]=;
// cout<<y<<" ";
}
}
}//cout<<endl;
/* for(int i=1;i<=n;i++)
cout<<vis[i]<<" ";*/
for(int i=;i<=n;i++)
if(!vis[i]) return ;
return ;
}
void topsort(){
priority_queue<int>q;
for(int i=;i<=n;i++)
if(du1[i]==)
q.push(i);
while(!q.empty()){
int x=q.top();q.pop();ans[++ans[]]=x;
for(int i=;i<e[x].size();i++){
int y=e[x][i];
du1[y]--;
if(du1[y]==)
q.push(y);
}
}
}
int main(){
/*freopen("1.in","r",stdin);
freopen("1.out","w",stdout);*/
T=read();
while(T--){
n=read();m=read();
memset(ans,,sizeof(ans));
memset(du,,sizeof(du));
memset(v,,sizeof(v));
memset(du1,,sizeof(du1));
memset(e,,sizeof(e));
for(int i=;i<=n;i++) edge[i].clear();
for(int i=,x,y;i<=m;i++){
x=read();y=read();
if(mp[T][make_pair(x,y)]) continue;
mp[T][make_pair(x,y)]=;
edge[x].push_back(y);
// e[x].push_back(y);
e[y].push_back(x);
du[y]++;
du1[x]++;
}
if(check()){
puts("Impossible!");
continue;
}
topsort();
for(int i=n;i>=;i--)
printf("%d ",ans[i]);
putchar('\n');
}
return ;
}

略丑,勿看

HNOI2015菜肴制作的更多相关文章

  1. bzoj 4010: [HNOI2015]菜肴制作 拓扑排序

    题目链接: 题目 4010: [HNOI2015]菜肴制作 Time Limit: 5 Sec Memory Limit: 512 MB 问题描述 知名美食家小 A被邀请至ATM 大酒店,为其品评菜肴 ...

  2. BZOJ 4010: [HNOI2015]菜肴制作( 贪心 )

    把图反向,然后按拓扑序贪心地从大到小选, 最后输出.set比priority_queue慢... --------------------------------------------------- ...

  3. P3243 [HNOI2015]菜肴制作(拓扑排序)

    P3243 [HNOI2015]菜肴制作 题目误导你正着做拓扑排序,然鹅你可以手造数据推翻它.于是就只能倒着做 我们开个优先队列,每次把可填的最大的编号取出来搞,最后倒着输出拓扑序就好辣 #inclu ...

  4. bzoj 4010 [HNOI2015]菜肴制作——贪心

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=4010 和 bzoj 2535 差不多.因为当前怎么决策与该点后面连的点的标号情况有关,所以按 ...

  5. 【BZOJ4010】[HNOI2015]菜肴制作 拓扑排序

    [BZOJ4010][HNOI2015]菜肴制作 Description 知名美食家小 A被邀请至ATM 大酒店,为其品评菜肴. ATM 酒店为小 A 准备了 N 道菜肴,酒店按照为菜肴预估的质量从高 ...

  6. BZOJ_4010_[HNOI2015]菜肴制作_拓扑排序+贪心

    BZOJ_4010_[HNOI2015]菜肴制作_拓扑排序+贪心 Description 知名美食家小 A被邀请至ATM 大酒店,为其品评菜肴. ATM 酒店为小 A 准备了 N 道菜肴,酒店按照为菜 ...

  7. [HNOI2015]菜肴制作 题解(自带口胡证明)

    [HNOI2015]菜肴制作 时间限制: 1 Sec  内存限制: 512 MB 题目描述 知名美食家小 A被邀请至ATM 大酒店,为其品评菜肴. ATM 酒店为小 A 准备了 N 道菜肴,酒店按照为 ...

  8. [HNOI2015]菜肴制作贪心的证明

    [HNOI2015]菜肴制作贪心的证明 先吐槽一句为什么网上都没人证这个东西,我觉得一点也不显然啊... 判环不用说了,现在处理一个DAG.考虑按题意模拟:建反图(边从后选的点连向先选的点),每次找全 ...

  9. 【题解】[HNOI2015]菜肴制作(贪心+topo序)

    [题解][HNOI2015]菜肴制作(贪心+topo序) 题意:请你构造一个排列\(p[i]\)使得对于数组\(arc[i]=p[i]\)的字典序最小,并且对于给定的有序数对\((u,v)\)保证你给 ...

  10. [bzoj4010][HNOI2015]菜肴制作_贪心_拓扑排序

    菜肴制作 bzoj-4010 HNOI-2015 题目大意:给定一张n个点m条边的有向图,求一个toposort,使得:(1)满足编号为1的点尽量在前:(2)满足(1)的情况下编号为2的点尽量在前,以 ...

随机推荐

  1. python 列表反转

    反转: 将原列表反转,返回None: li = [1, 2, 3]li.reverse()print(li)# [3, 2, 1]1234不改变原列表,返回反转后的新列表: li = [1, 2, 3 ...

  2. SpringBoot整合MyBatis的分页插件PageHelper

    1.导入依赖(maven) <dependency> <groupId>com.github.pagehelper</groupId> <artifactId ...

  3. hadoop面试题(自己整理版)

    1. hadoop 运行原理2. mapreduce 原理3. mapreduce 的优化4.举一个简单的例子说下 mapreduce 是怎么运行的5. hadoop 中 combiner 的作用6. ...

  4. vue入门:(class与style绑定)

    对象语法 数组语法 一.对象语法 1.1对象语法绑定HTML Class 语法:v-bind:class="{'className1':boolean1,'className2':boole ...

  5. asp.net Core 2.0 MVC为Controller或Action添加定制特性实现登录验证

    前言:最近在倒腾 微软的新平台 asp.net Core 2.0,在这个过程中有些东西还是存在差异.下面是我在学习过程的一点笔记.有不妥之处,望各位大虾指正! 一.先创建一个控制器继承于Control ...

  6. element-ui 中 el-table 根据scope.row行数据变化动态显示行内控件

    加入本行的数据为scope.row,其数据格式为 { "propertyId": 4, "propertyName": "标题", &quo ...

  7. Docker 容器数据卷(Data Volume)与数据管理

    卷(Volume)是容器中的一个数据挂载点,卷可以绕过联合文件系统,从而为Docker 提供持久数据,所提供的数据还可以在宿主机-容器或多个容器之间共享.通过卷,我们可以可以使修改数据直接生效,而不必 ...

  8. 4.ID主键生成策略

    保证唯一性(auto_increment) 一.xml方式 <?xml version="1.0"?> <!DOCTYPE hibernate-mapping P ...

  9. C# 中 ContextMenuStrip 和 ContextMenu区别

    简单来说,就是版本不同,只不过是升级后建议功能更加强大的ContextMenuStrip罢了,升级后的元件功能更强 . ContextMenu是VS2005里的,而ContextMenuStrip是V ...

  10. 小程序UI设计(9)-文字排版

    小程序中一般很少大段落的文字,基本是4.5个字的主题.一行标题.一行摘要.两行描述.显示时超出部分用省略号代替.下面结合工具使用介绍一下文字排版的方法.先看效果图.  工具中属性设置如下图:两行文字属 ...