这真是道神奇的题目:

原题链接

首先我们要证明以下的性质:

若原序列为\(\{a_n\}\),\(a_i\)和\(a_j\)不能同时放入一个栈中,当且仅当\(i<j,a_i<a_j\),且存在\(k\),\(s.t. \ k>j\)的同时有\(a_k<a_i\)。

原因很显然,因为有比\(a_i\)还小的元素在后面,若放入同一个栈中,必须先压栈压到\(a_k\),再弹出,但又因为会先弹出\(a_j\),序列的单调性就被破坏了。

所以对于每一对\(a_i\)和\(a_j\),我们都可以用上述性质来判断它们是否能在同一个栈中,再用后缀最大值优化一下,复杂度\(O(n^2)\)。

然后我们就有了这样的一些关系,我们该如何利用这些关系来判断序列是否合法呢?

二分图染色,对于不能在同一个栈中的两个位置,我们连一条无向边,然后dfs判断所有点能否二染色。如果能,序列就是合法的,否则不合法。

对于染色后的图,其实我们已经知道操作顺序了,又因为题目要求字典序最小,所以我们只用模拟一下,优先在栈\(S1\)上操作就行了。

上代码:

#include <bits/stdc++.h>

using namespace std;

#define wrap cout << endl

const int N = 1000;

int n, a[N+5], color[N+5], f[N+5], flag;
vector<int> G[N+5]; void addEdge(int u, int v) {
G[u].push_back(v);
G[v].push_back(u);
} void dfs(int u) {
for(int i = 0; i < G[u].size(); ++i) {
int v = G[u][i];
if(color[v]) {
if(color[v] == color[u])
flag = 1;
}
else {
color[v] = 3-color[u];
dfs(v);
}
}
} void solve() {
int cur = 1;
stack<int> s1, s2;
for(int i = 1; i <= n; ++i) { //模拟
if(color[i] == 1) s1.push(a[i]), cout << 'a' << " ";
if(color[i] == 2) s2.push(a[i]), cout << 'c' << " ";
while((!s1.empty() && s1.top() == cur) || (!s2.empty() && s2.top() == cur)) {
if(!s1.empty() && s1.top() == cur) s1.pop(), cout << 'b' << " ";
if(!s2.empty() && s2.top() == cur) s2.pop(), cout << 'd' << " ";
++cur;
}
}
} int main() {
cin >> n;
for(int i = 1; i <= n; ++i) cin >> a[i];
f[n+1] = 0x3f3f3f3f;
for(int i = n; i >= 1; --i) f[i] = min(f[i+1], a[i]);
for(int i = 1; i <= n; ++i)
for(int j = i+1; j <= n; ++j)
if(a[i] < a[j] && f[j+1] < a[i]) addEdge(i, j); //判断是否加边
for(int i = 1; i <= n; ++i)
if(!color[i])
color[i] = 1, dfs(i);
if(flag) {
cout << "0" << endl;
return 0;
}
solve();
return 0;
}

NOIp2018提高组 双栈排序的更多相关文章

  1. 双栈排序 2008年NOIP全国联赛提高组(二分图染色)

    双栈排序 2008年NOIP全国联赛提高组  时间限制: 1 s  空间限制: 128000 KB  题目等级 : 大师 Master     题目描述 Description Tom最近在研究一个有 ...

  2. [NOIP2008] 提高组 洛谷P1155 双栈排序

    题目描述 Tom最近在研究一个有趣的排序问题.如图所示,通过2个栈S1和S2,Tom希望借助以下4种操作实现将输入序列升序排序. 操作a 如果输入序列不为空,将第一个元素压入栈S1 操作b 如果栈S1 ...

  3. 【提高组NOIP2008】双栈排序 (twostack.pas/c/cpp)

    [题目描述] Tom最近在研究一个有趣的排序问题.如图所示,通过2个栈S1和S2,Tom希望借助以下4种操作实现将输入序列升序排序. 操作a 如果输入序列不为空,将第一个元素压入栈S1 操作b 如果栈 ...

  4. BZOJ 2080: [Poi2010]Railway 双栈排序

    2080: [Poi2010]Railway Time Limit: 10 Sec  Memory Limit: 259 MBSubmit: 140  Solved: 35[Submit][Statu ...

  5. 双栈排序(codevs 1170)题解

    [问题描述] Tom最近在研究一个有趣的排序问题.如图所示,通过2个栈S1和S2,Tom希望借助以下4种操作实现将输入序列升序排序. 操作a 如果输入序列不为空,将第一个元素压入栈S1 操作b 如果栈 ...

  6. [NOIp2018提高组]赛道修建

    [NOIp2018提高组]赛道修建 题目大意: 给你一棵\(n(n\le5\times10^4)\)个结点的树,从中找出\(m\)个没有公共边的路径,使得第\(m\)长的路径最长.问第\(m\)长的路 ...

  7. [NOIp2018提高组]货币系统

    [NOIp2018提高组]货币系统 题目大意: 有\(n(n\le100)\)种不同的货币,每种货币的面额为\([1,25000]\)之间的一个整数.若两种货币系统能够组合出来的数是相同的的,那我们就 ...

  8. NOIP2018提高组省一冲奖班模测训练(四)

    NOIP2018提高组省一冲奖班模测训练(四) 这次比赛只AC了第一题,而且花了40多分钟,貌似是A掉第一题里面最晚的 而且还有一个半小时我就放弃了…… 下次即使想不出也要坚持到最后 第二题没思路 第 ...

  9. NOIP2018提高组省一冲奖班模测训练(三)

    NOIP2018提高组省一冲奖班模测训练(三) 自己按照noip的方式考,只在最后一两分钟交了一次 第一题过了,对拍拍到尾. 第二题不会.考试时往组合计数的方向想,推公式,推了一个多小时,大脑爆炸,还 ...

随机推荐

  1. unity can't add the script behaviour CallbackExecutor. The script needs ...

    记一次Unity3D小问题 当我打开VS2017编辑完C#脚本,要将脚本拖到一个3D组件上时,发生了以下错误 unity can't add the script behaviour Callback ...

  2. 领域驱动设计(DDD:Domain-Driven Design)

    领域驱动设计(DDD:Domain-Driven Design) Eric Evans的"Domain-Driven Design领域驱动设计"简称DDD,Evans DDD是一套 ...

  3. SQL Server实际执行计划COST"欺骗"案例

    有个系统,昨天Support人员发布了相关升级脚本后,今天发现系统中有个功能不能正常使用了,直接报超时了(Timeout expired)的错误.定位到相关相关存储过程后,然后在优化分析的过程中,又遇 ...

  4. phpstorm设置编码格式

    phpstorm设置编码格式 默认: utf-8格式 设置方法: file -> settings -> Editor -> file encodng -> project e ...

  5. pyinstaller 打包selenium脚本 取消cmd

    更改源代码 找到文件(selenium->webdriver->common->service.py) 添加一个参数

  6. Redis原理

    RESP协议 支持tcp协议.基本数据类型,比如数组,字符串等,也可支持其他的通信场景. 模拟redis接收传输过来的set数据 //ServerSocket监听6379端口模拟redis publi ...

  7. Vue-异步组件

    一般情况下,在代码开头引入组件: import Vue from 'vue' import Router from 'vue-router' import Home from '@/pages/hom ...

  8. 2017-8-2新开了一个ABP交流的QQ群(291304962 ),欢迎加入

    因为ABP架构设计交流群人数一直爆满,很多想交流ABP的朋友无法加进群里, 刚新建了一个QQ群,群号291304962(ABP架构设计交流群3),欢迎对ABP感兴趣的朋友加入. 欢迎加QQ群: ABP ...

  9. Golang 入门系列(七) Redis的使用

    安装 1. Redis 的安装很简单,我这里测试直接用的是windows 的版本.如何安装就不细说了.想了解的可以看之前的文章:https://www.cnblogs.com/zhangweizhon ...

  10. 如何用ABP框架快速完成项目(6) - 用ABP一个人快速完成项目(2) - 使用多个成熟控件框架

    正如我在<office365的开发者训练营,免费,在微软广州举办>课程里面所讲的, 站在巨人的肩膀上的其中一项就是, 尽量使用别人成熟的框架. 其中也包括了控件框架   abp和52abp ...