CF 1023D Array Restoration - 线段树
题解
非常容易想到的线段树, 还可以用并查集来。 还有一位大神用了$O(n)$ 就过了Orz
要判断是否能染色出输入给出的序列,必须满足两个条件:
1、 序列中必须存在一个$q$
2、 两个相同的数$x$的中间不存在比 $ x$ 小的数
首先判断输入的数列中是否存在$q$, 若不存在$q$ 且没有 $a_i = 0$, 表示序列中一定没有$q$, 直接输出NO
若存在某个$a_i = 0$ , 将任意一个染成$q$即可
然后我们再查询两个相同的数$x$ 中是否存在比$x$ 小的数,用线段树来维护区间最小即可实现
接着把两个$x$中间的序列染色, 用MinOK来记录,表示区间内$a_i = 0$,可以染色的最小值。 (线段树区间修改
最后把$a_i = 0$ 进行染色(利用线段树点查询
CF现场就想到的算法,然而没有特判存在$q$,pushdown还少打了唔, CF百分百掉分,我要变成pupil了,太惨啦QAQ
代码
#include<cstring>
#include<algorithm>
#include<cstdio>
#define lson nd<<1
#define rson nd<<1|1
#define rd read()
#define rep(i,a,b) for(int i = (a); i <= (b); ++i)
#define per(i,a,b) for(int i = (a); i >= (b); --i)
using namespace std; const int N = 3e5, inf = ~0U >> ; int MIN[N << ], a[N], L[N], R[N], lazy[N << ], q, n, pos;
int Mok[N << ]; int read() {
int X = , p = ; char c = getchar();
for(; c > '' || c < ''; c = getchar()) if( c == '-') p = -;
for(; c >= '' && c <= ''; c = getchar()) X = X * + c - '';
return X * p;
} void update(int nd) {
MIN[nd] = min(MIN[lson], MIN[rson]);
} void pushdown(int nd) {
if(lazy[nd]) {
Mok[lson] = lazy[nd];
Mok[rson] = lazy[nd];
lazy[lson] = lazy[rson] = lazy[nd];
lazy[nd] = ;
}
} void build(int l, int r, int nd) {
if(l == r) {
MIN[nd] = a[l] == ? inf : a[l];
return;
}
int mid = (l + r) >> ;
build(l, mid, lson);
build(mid + , r, rson);
update(nd);
} int query(int Li, int Ri, int l, int r, int nd) {//查询区间最小
if(Li <= l && r <= Ri) return MIN[nd];
int mid = (l + r) >> , re = inf;
if(Li <= mid) re = min(re, query(Li, Ri, l, mid, lson));
if(mid < Ri) re = min(re, query(Li, Ri, mid + , r, rson));
return re;
} int query_pt(int p, int l, int r, int nd) {//查询可以染上的值
if(l == r) return Mok[nd];
int mid = (l + r) >> ;
pushdown(nd);
if(p <= mid) return query_pt(p, l, mid, lson);
else return query_pt(p, mid + , r, rson);
} void change(int Li, int Ri, int c, int l, int r, int nd) {
if(Li <= l && r <= Ri) {
lazy[nd] = c;
Mok[nd] = c;
return;
}
int mid = (l + r) >> ;
pushdown(nd);
if(Li <= mid) change(Li, Ri, c, l, mid, lson);
if(mid < Ri) change(Li, Ri, c, mid + , r, rson);
update(nd);
} int main()
{
n = rd; q = rd;
for(int i = ; i <= n; ++i) {
a[i] = rd;
if(!a[i]) pos = i;
if(!L[a[i]]) L[a[i]] = i;
R[a[i]] = i;
}
if(!L[q] && !pos) return printf("NO\n"), ;//无a[i]=0也无q
build(, n, );
for(int i = ; i <= q; ++i) {//必须按颜色从小到大覆盖
if(!L[i]) continue;
int minv = query(L[i], R[i], , n, );
if(minv < i) return printf("NO\n"), ;
change(L[i], R[i], i, , n, );
}
for(int i = ; i <= n; ++i) if(!a[i]) {
a[i] = query_pt(i, , n, );
if(i == pos && !L[q]) a[i] = q; // 必须存在q
else if(!a[i]) a[i] = ;
}
printf("YES\n");
for(int i = ; i <= n; ++i) printf("%d ", a[i]);
putchar('\n');
}
CF 1023D Array Restoration - 线段树的更多相关文章
- Codeforces #504(div1+div2) 1023D Array Restoration(线段树)
题目大意:给你一个数组,数组是经过q次区间覆盖后的结果,第i次覆盖是把区间内的值赋值为i,其中有若干个地方数值未知(就是0),让你判断这个数组是否可以经过覆盖后得到的,如果可以,输出任意一种可行数组. ...
- CF1114F Please, another Queries on Array?(线段树,数论,欧拉函数,状态压缩)
这题我在考场上也是想出了正解的……但是没调出来. 题目链接:CF原网 题目大意:给一个长度为 $n$ 的序列 $a$,$q$ 个操作:区间乘 $x$,求区间乘积的欧拉函数模 $10^9+7$ 的值. ...
- Codedforces 1076G Array Game 线段树
题意 现在cf上看题意真nm麻烦,有道网页翻译和谷歌翻译鬼畜的一匹 两个人在玩一个游戏. 有一个有\(n\)个数序列\(B\),一开始有一个棋子在\(B\)的第一个位置. 双方轮流操作,第一次操作前将 ...
- codeforces 482B. Interesting Array【线段树区间更新】
题目:codeforces 482B. Interesting Array 题意:给你一个值n和m中操作,每种操作就是三个数 l ,r,val. 就是区间l---r上的与的值为val,最后问你原来的数 ...
- CF 787D Legacy(线段树思想构图+最短路)
D. Legacy time limit per test 2 seconds memory limit per test 256 megabytes input standard input out ...
- Light OJ-1082 - Array Queries,线段树区间查询最大值,哈哈,水过~~
...
- Codeforces E. Interesting Array(线段树)
题目描述: D. Interesting Arraytime limit per test1 secondmemory limit per test256 megabytesinputstandard ...
- B. Interesting Array(线段树)
B. Interesting Array time limit per test 1 second memory limit per test 256 megabytes input standard ...
- CF 19D Points 【线段树+平衡树】
在平面上进行三种操作: 1.add x y:在平面上添加一个点(x,y) 2.remove x y:将平面上的点(x,y)删除 3.find x y:在平面上寻找一个点,使这个点的横坐标大于x,纵坐标 ...
随机推荐
- var与dynamic
var与dynamic 如果你用MVC写过程序,那么你应该知道ViewBag这个用于前后台的数据传递工具,那么你是否对ViewBag的用法感到过疑惑呢? ViewBag.Mode1l=new obje ...
- 清理mysql binlog日志
1.查看binlog日志 mysql> show binary logs; +------------------+------------+| Log_name | File_ ...
- Jenkins邮件扩展(Email Extension插件 Windows环境)
1.Jenkins ver. 2.107.3版本自带Email Extension插件启动后即可看到系统设置里的 Extended E-mail Notification ,如果没有请安装 2.安装过 ...
- etcd查看key-value
get/set key-value etcdctl get/set /key-path etcdctl watch --recursive /test/sm/default/apps 查看所有key- ...
- 《GPU高性能编程CUDA实战》附录三 关于book.h
▶ 本书中用到的公用函数放到了头文件book.h中 #ifndef __BOOK_H__ #define __BOOK_H__ #include <stdio.h> #include &l ...
- bootstrap左侧边栏
之前都是想直接把导航栏放左边,但是会占一整行 网上找了好久,看到用bootstrap响应式布局,可以比较简单实现 经典的,可以参考:http://demo.qianduanblog.com/3150/ ...
- 基于二进制RPC协议法的轻量级远程调用框架 ---- Hessian
使用Java创建Hessian服务有四个步骤: 1.创建Java接口作为公共API (client和server端 创建一个相同的借口) 2.使 ...
- Haskell语言学习笔记(68)HDBC
安装 HDBC-Sqlite3 $ cabal install HDBC-Sqlite3 Installed HDBC-sqlite3-2.3.3.1 Prelude> :m Database. ...
- Haskell语言学习笔记(46)Parsec(3)
Applicative Parsing 使用 Applicative 式的 Parser. 包括使用 (<$>), (<*>), (<$), (<*), (*> ...
- Spring Cloud feign
Spring Cloud feign使用 前言 环境准备 应用模块 应用程序 应用启动 feign特性 综上 1. 前言 我们在前一篇文章中讲了一些我使用过的一些http的框架 服务间通信之Http框 ...