Codeforces 934.C A Twisty Movement
1 second
256 megabytes
standard input
standard output
A dragon symbolizes wisdom, power and wealth. On Lunar New Year's Day, people model a dragon with bamboo strips and clothes, raise them with rods, and hold the rods high and low to resemble a flying dragon.
A performer holding the rod low is represented by a 1, while one holding it high is represented by a 2. Thus, the line of performers can be represented by a sequence a1, a2, ..., an.
Little Tommy is among them. He would like to choose an interval [l, r] (1 ≤ l ≤ r ≤ n), then reverse al, al + 1, ..., ar so that the length of the longest non-decreasing subsequence of the new sequence is maximum.
A non-decreasing subsequence is a sequence of indices p1, p2, ..., pk, such that p1 < p2 < ... < pk and ap1 ≤ ap2 ≤ ... ≤ apk. The length of the subsequence is k.
The first line contains an integer n (1 ≤ n ≤ 2000), denoting the length of the original sequence.
The second line contains n space-separated integers, describing the original sequence a1, a2, ..., an (1 ≤ ai ≤ 2, i = 1, 2, ..., n).
Print a single integer, which means the maximum possible length of the longest non-decreasing subsequence of the new sequence.
4
1 2 1 2
4
10
1 1 2 2 2 1 1 2 2 1
9
In the first example, after reversing [2, 3], the array will become [1, 1, 2, 2], where the length of the longest non-decreasing subsequence is 4.
In the second example, after reversing [3, 7], the array will become [1, 1, 1, 1, 2, 2, 2, 2, 2, 1], where the length of the longest non-decreasing subsequence is 9.
题目大意:给一个只有1,2组成的序列,要求翻转一个区间,使得最长不下降子序列尽可能长.
分析:读错题坑了我40分钟.子序列可以不连续!
考虑没有翻转操作.那么答案肯定是一个位置左边的1的数量+右边的2的数量,取max. 那么我们可以统计1的前缀和,2的后缀和.
如果有翻转操作.其实就是翻转的区间中的一个位置统计1的后缀和,同时在这个位置统计2的前缀和,最后和两个端点处的相减.
具体来说,如果记sum1为1的前缀和,sum2为2的后缀和,sum3为1的后缀和,sum4为2的前缀和,翻转的两个区间端点为a,b.那么答案就是max{sum1[a - 1] + sum2[b + 1] + sum3[i + 1] - sum3[b + 1] + sum4[i] - sum4[a - 1]}.实际上变动的就是sum3[i + 1]与sum4[i],求出一个区间内它们的最大值,有很多方法.我偷懒用线段树维护.
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm> using namespace std; typedef long long ll; int n,a[],ans,f[][],sum1[],sum2[],sum3[],sum4[],b[],maxx[ << ]; void pushup(int o)
{
maxx[o] = max(maxx[o * ],maxx[o * + ]);
} void build(int o,int l,int r)
{
if (l == r)
{
maxx[o] = b[l];
return;
}
int mid = (l + r) >> ;
build(o * ,l,mid);
build(o * + ,mid + ,r);
pushup(o);
} int query(int o,int l,int r,int x,int y)
{
if (x <= l && r <= y)
return maxx[o];
int mid = (l + r) >> ,res = -;
if (x <= mid)
res = max(res,query(o * ,l,mid,x,y));
if (y > mid)
res = max(res,query(o * + ,mid + ,r,x,y));
return res;
} int main()
{
scanf("%d",&n);
for (int i = ; i <= n; i++)
scanf("%d",&a[i]);
for (int i = ; i <= n; i++)
sum1[i] = sum1[i - ] + (a[i] == ? : );
for (int i = n; i >= ; i--)
sum2[i] = sum2[i + ] + (a[i] == ? : );
for (int i = n; i >= ; i--)
sum3[i] = sum3[i + ] + (a[i] == ? : );
for (int i = ; i <= n; i++)
sum4[i] = sum4[i - ] + (a[i] == ? : );
for (int i = ; i <= n; i++)
b[i] = sum4[i] + sum3[i + ];
build(,,n);
for (int i = ; i <= n; i++)
{
for (int j = i; j <= n; j++)
{
int temp = query(,,n,i - ,j);
ans = max(ans,sum1[i - ] + sum2[j + ] + temp - sum3[j + ] - sum4[i - ]);
}
}
printf("%d\n",ans); return ;
}
Codeforces 934.C A Twisty Movement的更多相关文章
- Codeforces 934 C.A Twisty Movement-前缀和+后缀和+动态规划
C. A Twisty Movement time limit per test 1 second memory limit per test 256 megabytes input standa ...
- 【Codeforces 933A】A Twisty Movement
[链接] 我是链接,点我呀:) [题意] [题解] 因为只有1和2. 所以最后肯定是若干个1接着若干个2的情况. 即11...11222...222这样的. 1.首先考虑没有翻转的情况. 那么就直接枚 ...
- Codeforces 934C - A Twisty Movement
934C - A Twisty Movement 思路:dp 很容易想到要预处理出1的前缀和pre[i]和2的后缀和suf[i] 然后枚举区间,对于每个区间如果能求出最长递减序列的长度,那么就能更新答 ...
- Codeforces Round #462 (Div. 2) C. A Twisty Movement
C. A Twisty Movement time limit per test1 second memory limit per test256 megabytes Problem Descript ...
- [Codeforces 933A]A Twisty Movement
Description 题库链接 给你一个长度为 \(n\) 的只含有 \(1,2\) 的序列.你可以选择其中的一段 \([l,r]\) ,将区间翻转,翻转后使得单调不下降序列最长.求最长长度. \( ...
- Codeforces Round #462 (Div. 2), problem: (C) A Twisty Movement (求可以转一次区间的不递增子序列元素只有1,2)
题目意思: 给长度为n(n<=2000)的数字串,数字只能为1或者2,可以将其中一段区间[l,r]翻转,求翻转后的最长非递减子序列长度. 题解:求出1的前缀和,2的后缀和,以及区间[i,j]的最 ...
- 【Codeforces Round #462 (Div. 1) A】 A Twisty Movement
[链接] 我是链接,点我呀:) [题意] 在这里输入题意 [题解] ans初值值为a[1..n]中1的个数. 接下来考虑以2为结尾的最长上升子序列的个数. 枚举中间点i. 计算1..i-1中1的个数c ...
- Codeforces 934 A.Compatible Pair
http://codeforces.com/contest/934 A. A Compatible Pair time limit per test 1 second memory limit p ...
- A. A Twisty Movement dp
https://codeforces.com/problemset/problem/933/A 这个是一个dp,但是我并没有看出来,然后也不太会写, 这种题一般应该要想到先预处理前缀和后缀,然后再进行 ...
随机推荐
- hive的内置函数和自定义函数
一.内置函数 1.一般常用函数 .取整函数 round() 当传入第二个参数则为精度 bround() 银行家舍入法:为5时,前一位为偶则舍,奇则进. .向下取整 floor() .向上取整 ceil ...
- 技本功丨请带上纸笔刷着看:解读MySQL执行计划的type列和extra列
本萌最近被一则新闻深受鼓舞,西工大硬核“女学神”白雨桐,获6所世界顶级大学博士录取 货真价值的才貌双全,别人家的孩子 高考失利与心仪的专业失之交臂,选择了软件工程这门自己完全不懂的专业.即便全部归零, ...
- [Linux] Migrate plugins and setting for vim
Hot to migrate plugins and setting for vim from one computer to another ? Just copy ~/.vim and ~/.v ...
- 6. B树
一.B 树是一种多叉平衡查找树 相较于二叉结构的红黑树,B 树是多叉结构,所以在元素数量非常多的情况下,B 树的高度不会像二叉树那么大,从而保证查询效率. 一棵含 n 个结点的 B 树的高度 h = ...
- Scrum立会报告+燃尽图 05
此作业要求参见:[https://edu.cnblogs.com/campus/nenu/2018fall/homework/2195] 一.小组介绍 组长:王一可 组员:范靖旋,王硕,赵佳璐,范洪达 ...
- 第三次c++作业
https://github.com/egoistor/3Elevators-scheduling 老实说,因为这周时间紧张,(高数的期中考和一些奇奇怪怪的时期), 所以代码大体是有,但是很多细节处理 ...
- 软工实践-Alpha 冲刺 (10/10)
队名:起床一起肝活队 组长博客:博客链接 作业博客:班级博客本次作业的链接 组员情况 组员1(队长):白晨曦 过去两天完成了哪些任务 描述: 完成所有界面的链接,整理与测试 展示GitHub当日代码/ ...
- Spring学习(七)——增强类
Spring 切点 什么是切点?切点(Pointcut),每个程序类都拥有多个连接点,如一个拥有两个方法的类,这两个方法都是连接点,即连接点是程序类中客观存在的事物.但在这为数从多的连接点中,如何定位 ...
- lintcode-402-连续子数组求和
[402-连续子数组求和(http://www.lintcode.com/zh-cn/problem/continuous-subarray-sum/) 给定一个整数数组,请找出一个连续子数组,使得该 ...
- iOS- Swift:使用FMDB进行数据库操作(线程安全:增删改查)
1.前言 GitHub上2000多颗星的FMDB数据库框架想来大家都很熟悉, 今天用Swift对其进行了一个完成的数据存储读流程 写完之后用博客分享之,与大家一起交流, 希望对需要的朋友提供些帮助 ...