HDU 4747 Mex
4747
思路:
线段树
先求出mex(1,1), mex(1, 2) , mex(1,3),...,mex(1,n)(单调上升),先将这些mex放进线段树里求和
然后再求出next[i]表示下一次出现a[i] 的位置
然后从前往后不停的删数,对于一个数a[i],我们删掉他的影响是:l为mex大于a[i]的位置,r 为next[i],l 到 r-1 之间的 mex都变为 a[i]
然后这个线段树只需要维护区间最大值(方便查找第一个大于a[i]的位置)和区间和就可以了
代码:
#include<bits/stdc++.h> using namespace std; #define fi first #define se second #define pi acos(-1.0) #define LL long long //#define mp make_pair #define pb push_back #define ls rt<<1, l, m #define rs rt<<1|1, m+1, r #define ULL unsigned LL #define pll pair<LL, LL> #define pii pair<int, int> #define mem(a, b) memset(a, b, sizeof(a)) #define fio ios::sync_with_stdio(false);cin.tie(0);cout.tie(0); #define fopen freopen("in.txt", "r", stdin);freopen("out.txt", "w", stout); //headconst int N = 2e5 + 5; int a[N], nxt[N], mx[N<<2], lazy[N<<2], mex[N]; LL sum[N<<2]; map<int, int>mp; void push_up(int rt) {sum[rt] = sum[rt<<1] + sum[rt<<1|1];mx[rt] = max(mx[rt<<1], mx[rt<<1|1]); } void push_down(int rt, int len) {sum[rt<<1] = 1LL * lazy[rt] * (len - (len >> 1));mx[rt<<1] = lazy[rt];lazy[rt<<1] = lazy[rt];sum[rt<<1|1] = 1LL * lazy[rt] * (len >> 1);mx[rt<<1|1] = lazy[rt];lazy[rt<<1|1] = lazy[rt];lazy[rt] = 0; } void build(int rt, int l, int r) {if(l == r) {mx[rt] = sum[rt] = mex[l];return ;}int m = (l+r) >> 1;build(ls);build(rs);push_up(rt); } void update(int x, int L, int R, int rt, int l, int r) {if(L <= l && r <= R) {mx[rt] = x;sum[rt] = 1LL * (r-l+1) * x;lazy[rt] = x;return ;}if(lazy[rt]) push_down(rt, r-l+1);int m = (l+r) >> 1;if(L <= m) update(x, L, R, ls);if(R > m) update(x, L, R, rs);push_up(rt); } LL query(int L, int R, int rt, int l, int r) {if(L <= l && r <= R) return sum[rt];if(lazy[rt]) push_down(rt, r-l+1);int m = (l+r) >> 1;LL ans = 0;if(L <= m) ans += query(L, R, ls);if(R > m) ans += query(L, R, rs);push_up(rt);return ans; } int Find(int x, int rt, int l, int r) {if(l == r) return l;int m = (l+r) >> 1;if(lazy[rt]) push_down(rt, r-l+1);if(mx[rt<<1] > x) return Find(x, ls);else return Find(x, rs); } int main() {int n;while(~scanf("%d", &n) && n) {mem(lazy, 0);build(1, 1, n);for (int i = 1; i <= n; i++) scanf("%d", &a[i]);mp.clear();int tmp = 0;for (int i = 1; i <= n; i++) {mp[a[i]]++;while(mp.find(tmp) != mp.end()) tmp++;mex[i] = tmp;}build(1, 1, n);mp.clear();for (int i = n; i >= 1; i--) {if(mp.find(a[i]) == mp.end()) nxt[i] = n+1;else nxt[i] = mp[a[i]];mp[a[i]] = i;}LL ans = 0;for (int i = 1; i <= n; i++) {ans += query(1, n, 1, 1, n);if(mx[1] <= a[i]) continue;int l = Find(a[i], 1, 1, n);int r = nxt[i];if(l < r) update(a[i], l, r-1, 1, 1, n);}printf("%lld\n", ans);}return 0; }
转载于:https://www.cnblogs.com/widsom/p/9118494.html
HDU 4747 Mex相关推荐
- hdu 4747 mex 线段树+思维
http://acm.hdu.edu.cn/showproblem.php?pid=4747 题意: 我们定义mex(l,r)表示一个序列a[l]....a[r]中没有出现过得最小的非负整数, 然后我 ...
- HDU 4747 Mex【线段树上二分+扫描线】
[题意概述] 一个区间的Mex为这个区间没有出现过的最小自然数,现在给你一个序列,要求求出所有区间的Mex的和. [题解] 扫描线+线段树. 我们在线段树上维护从当前左端点开始的前缀Mex,显然从左到 ...
- HDU - 4747 Mex(线段树)
题意: 计算 其中mex即为博弈中出现的mex(未出现的最小非负整数). 分析: 有两种方法,递推有点懵(以后再来补QAQ),就写了线段树 想法是每次求以i为起点的区间的mex值的和,最后累加即 ...
- HDOJ 4747 Mex
非常好的线段树题....此题必定会火..... Mex Time Limit: 15000/5000 MS (Java/Others) Memory Limit: 65535/65535 K ( ...
- 动态规划总结与题目分类
源博客链接:http://blog.csdn.net/cc_again/article/details/25866971 动态规划一直是ACM竞赛中的重点,同时又是难点,因为该算法时间效率高,代码量少 ...
- 『ACM-算法-动态规划』初识DP动态规划算法
一.多阶段决策过程的最优化问题 在现实生活中,有类活 动的过程,由于 它的特殊性,可将过程分成若干个互相阶段.在它的每一阶段都需要作出决策,从而使整个过程达到最好的活动效果.当阶段决策的选取不是任意确 ...
- (转)dp动态规划分类详解
dp动态规划分类详解 转自:http://blog.csdn.NET/cc_again/article/details/25866971 动态规划一直是ACM竞赛中的重点,同时又是难点,因为该算法时间 ...
- 《动态规划》— 动态规划分类
动态规划(英语:Dynamic programming,DP)是一种在数学.计算机科学和经济学中使用的,通过把原问题分解为相对简单的子问题的方式求解复杂问题的方法. 动态规划常常适用于有重叠子问题和最 ...
- 转:动态规划题目分类
https://blog.csdn.net/cc_again/article/details/25866971 一.简单基础dp 这类dp主要是一些状态比较容易表示,转移方程比较好想,问题比较基本常见 ...
最新文章
- 浅谈 JavaScriptCore
- 长江存储年底提供自研32层堆叠3D NAND闪存样品
- (专题二)01 矩阵的处理-特殊矩阵
- python methodtype_Python的实例定属性和方法或类绑定方法
- 如何做一个有品位的程序员
- OpenCV :(-5:Bad argument) Matrix operand is an empty matrix. in function ‘checkOperandsExist‘
- 姐们儿,你就忍了吧—咱们一起骂老板(4)
- python股票收益率计算_股票分析之——收益率(附完整代码和讲解)
- 使用Python、pandas、pyecharts进行数据分析——实例讲解
- java word书签_java和javascript获取word的 书签位置
- 朴素贝叶斯——新闻分类
- 车牌规格以及识别中的不利因素
- ERP系统具有哪些功能?
- 金庸武侠内功排行榜TOP10
- mysql取第一行数据_select取第一行数据
- 新番 | 万万没想到,Hulu有一天也开始推新番了
- 整型转换为32位二进制字符串
- 6只做化验用的玻璃杯,前面3只盛满了水,后面3只是空的。你能只移动1只玻璃杯,就便盛满水的杯子和空杯子间隔起来吗?
- 零一背包问题(一维列表逆序的解释)
- c语言成绩筛选,c语言筛选质数