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,但是我并没有看出来,然后也不太会写, 这种题一般应该要想到先预处理前缀和后缀,然后再进行 ...
随机推荐
- IncDec序列:差分+贪心
IncDec序列 题目描述: 给定一个长度为 n 的数列 a1,a2,…,an,每次可以选择一个区间[l,r],使下标在这个区间内的数都加一或者都减一. 求至少需要多少次操作才能使数列中的所有数都一样 ...
- Node2vec 代码分析
Node2vec 代码从Github上clone到本地,主要是main.py和node2vec.py两个文件. 下面把我的读代码注释放到上面来, import numpy as np import n ...
- Scrum立会报告+燃尽图(Beta阶段第四次)
此作业要求参见:https://edu.cnblogs.com/campus/nenu/2018fall/homework/2386 项目地址:https://coding.net/u/wuyy694 ...
- JNDI和JDBC
没有JNDI的做法:程序员开发时,知道要开发访问MySQL数据库的应用,于是将一个对 MySQL JDBC 驱动程序类的引用进行了编码,并通过使用适当的 JDBC URL 连接到数据库.就像以下代码这 ...
- Spark Shuffle之Hash Shuffle
源文件放在github,如有谬误之处,欢迎指正.原文链接https://github.com/jacksu/utils4s/blob/master/spark-knowledge/md/hash-sh ...
- Struts2(四)
以下内容是基于导入struts2-2.3.32.jar包来讲的 1.struts2配置文件加载的顺序 struts2的StrutsPrepareAndExecuteFilter拦截器中对Dispatc ...
- PAT 甲级 1059 Prime Factors
https://pintia.cn/problem-sets/994805342720868352/problems/994805415005503488 Given any positive int ...
- 遍历frame中的表单:
遍历frame中的表单: public void table1() { // 查找frame List<WebElement> iframes = driver.findElements( ...
- Mysql中关键词执行顺序
MySQL的语句执行顺序 MySQL的语句一共分为11步,最先执行的总是FROM操作,最后执行的是LIMIT操作.其中每一个操作都会产生一张虚拟的表,这个虚拟的表作为一个处理的输入,只是这些虚拟的表对 ...
- CDN加速-内容分发网络
内容分发网络 (互联网技术) 编辑 CDN的全称是Content Delivery Network,即内容分发网络.其基本思路是尽可能避开互联网上有可能影响数据传输速度和稳定性的瓶颈和环节,使内容传输 ...