AtCoder Regular Contest 066 E - Addition and Subtraction Hard (结论+DP)
Time limit : 2sec / Memory limit : 256MB
Score : 900 points
Problem Statement
Joisino has a formula consisting of N terms: A1 op1 A2 … opN−1 AN. Here, Ai is an integer, and opi is an binary operator either + or -. Because Joisino loves large numbers, she wants to maximize the evaluated value of the formula by inserting an arbitrary number of pairs of parentheses (possibly zero) into the formula. Opening parentheses can only be inserted immediately before an integer, and closing parentheses can only be inserted immediately after an integer. It is allowed to insert any number of parentheses at a position. Your task is to write a program to find the maximum possible evaluated value of the formula after inserting an arbitrary number of pairs of parentheses.
Constraints
- 1≦N≦105
- 1≦Ai≦109
- opi is either
+or-.
Input
The input is given from Standard Input in the following format:
N
A1 op1 A2 … opN−1 AN
Output
Print the maximum possible evaluated value of the formula after inserting an arbitrary number of pairs of parentheses.
Sample Input 1
3
5 - 1 - 3
Sample Output 1
7
The maximum possible value is: 5−(1−3)=7.
Sample Input 2
5
1 - 2 + 3 - 4 + 5
Sample Output 2
5
The maximum possible value is: 1−(2+3−4)+5=5.
Sample Input 3
5
1 - 20 - 13 + 14 - 5
Sample Output 3
13
The maximum possible value is: 1−(20−(13+14)−5)=13.
题意:
给你一个只含有数字和加减号的字符串表达式,你可以加无数个括号,来改变运算顺序。
让你求出这个表达式能表达的最大的结果值。
思路:
首先我们要知道这个结论,
即一个表达式最多有效 括号最多是两层,因为只有在负号后面加括号才有作用,那么一个括号对括号里面的数值的影响是取负号一次,两层是取一部分是负,一部分是正(两层里的),如果有三层,那么第三层提取到最外边一层不会改变数值。
那么我们即可定义dp的状态
dp[i][j] 表示到第i个数时,第i个数后面有j个括号时,表示式的最大值。
那么我们来分析一下转移:
我们从i-1转移到i
当是‘+’时
我们可以在 dp[i-1][j] 后面直接加上 a[i] 即可转移到 dp[i][0]
在d[i-1][1] 括号里 加入a[i] ,贡献值为 - a[i] ,可以转移到dp[i][1]
dp[i-1][2] 最里层括号加入a[i] ,贡献值 为+ a[i] 可以转移到dp[i][2]
当是'-' 时
我们默认减号后面必须加括号,即使只包括自己 即这样的 - ( a[i] )
那么我们把负号后面的dp[i][0] = -inf ,即无穷小,不影响我们其他的运算。
我们可以在 dp[i-1][0/1 ]后面加上 -(a[i]) 即转移到 dp[i-1][1]
在dp[i-1][1]的括号里面加上 - (a[i] ),或者dp[i-1][2] 的外层括号里加上 - (a[i])
转移到dp[i][2] ,数值贡献时 +a[i]
这样就把全部的转移表示出来了,注意开ll。
细节见代码:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <queue>
#include <stack>
#include <map>
#include <set>
#include <vector>
#include <iomanip>
#define ALL(x) (x).begin(), (x).end()
#define rt return
#define dll(x) scanf("%I64d",&x)
#define xll(x) printf("%I64d\n",x)
#define sz(a) int(a.size())
#define all(a) a.begin(), a.end()
#define rep(i,x,n) for(int i=x;i<n;i++)
#define repd(i,x,n) for(int i=x;i<=n;i++)
#define pii pair<int,int>
#define pll pair<long long ,long long>
#define gbtb ios::sync_with_stdio(false),cin.tie(0),cout.tie(0)
#define MS0(X) memset((X), 0, sizeof((X)))
#define MSC0(X) memset((X), '\0', sizeof((X)))
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define eps 1e-6
#define gg(x) getInt(&x)
#define db(x) cout<<"== [ "<<x<<" ] =="<<endl;
using namespace std;
typedef long long ll;
ll gcd(ll a,ll b){return b?gcd(b,a%b):a;}
ll lcm(ll a,ll b){return a/gcd(a,b)*b;}
ll powmod(ll a,ll b,ll MOD){ll ans=;while(b){if(b%)ans=ans*a%MOD;a=a*a%MOD;b/=;}return ans;}
inline void getInt(int* p);
const int maxn=;
// const int inf=0x3f3f3f3f;
/*** TEMPLATE CODE * * STARTS HERE ***/
int n;
char op[maxn];
int a[maxn];
ll dp[maxn/][];
const ll inf=(ll)(1e18); int main()
{
//freopen("D:\\common_text\\code_stream\\in.txt","r",stdin);
//freopen("D:\\common_text\\code_stream\\out.txt","w",stdout);
gbtb;
cin>>n;
cin>>a[];
repd(i,,n)
{
cin>>op[i]>>a[i];
}
dp[][]=a[];
dp[][]=dp[][]=-inf;
repd(i,,n)
{
if(op[i]=='+')
{
dp[i][]=max(dp[i-][],max(dp[i-][],dp[i-][]))+a[i];
dp[i][]=dp[i-][]-a[i];
dp[i][]=dp[i-][]+a[i];
}else
{
dp[i][]=-inf;
dp[i][]=max(dp[i-][],dp[i-][])-a[i];
dp[i][]=max(dp[i-][],dp[i-][])+a[i];
}
}
cout<<max(dp[n][],max(dp[n][],dp[n][]))<<endl; return ; } inline void getInt(int* p) {
char ch;
do {
ch = getchar();
} while (ch == ' ' || ch == '\n');
if (ch == '-') {
*p = -(getchar() - '');
while ((ch = getchar()) >= '' && ch <= '') {
*p = *p * - ch + '';
}
}
else {
*p = ch - '';
while ((ch = getchar()) >= '' && ch <= '') {
*p = *p * + ch - '';
}
}
}
AtCoder Regular Contest 066 E - Addition and Subtraction Hard (结论+DP)的更多相关文章
- AtCoder Regular Contest 066 F Contest with Drinks Hard
题意: 你现在有n个题目可以做,第i个题目需要的时间为t[i],你要选择其中的若干题目去做.不妨令choose[i]表示第i个题目做不做.定义cost=∑(i<=n)∑(i<=j<= ...
- Atcoder Regular Contest 066 F genocide【JZOJ5451】
题目 分析 \(s[i]\)表示a前缀和. 设\(f[i]\)表示做完了1~i的友谊颗粒的最优值(不一定选i),那么转移方程为 \[f[i]=max\{f[i-1],max\{f[j]-s[i]+s[ ...
- AtCoder Regular Contest 061
AtCoder Regular Contest 061 C.Many Formulas 题意 给长度不超过\(10\)且由\(0\)到\(9\)数字组成的串S. 可以在两数字间放\(+\)号. 求所有 ...
- AtCoder Regular Contest 094 (ARC094) CDE题解
原文链接http://www.cnblogs.com/zhouzhendong/p/8735114.html $AtCoder\ Regular\ Contest\ 094(ARC094)\ CDE$ ...
- AtCoder Regular Contest 092
AtCoder Regular Contest 092 C - 2D Plane 2N Points 题意: 二维平面上给了\(2N\)个点,其中\(N\)个是\(A\)类点,\(N\)个是\(B\) ...
- AtCoder Regular Contest 093
AtCoder Regular Contest 093 C - Traveling Plan 题意: 给定n个点,求出删去i号点时,按顺序从起点到一号点走到n号点最后回到起点所走的路程是多少. \(n ...
- AtCoder Regular Contest 094
AtCoder Regular Contest 094 C - Same Integers 题意: 给定\(a,b,c\)三个数,可以进行两个操作:1.把一个数+2:2.把任意两个数+1.求最少需要几 ...
- AtCoder Regular Contest 095
AtCoder Regular Contest 095 C - Many Medians 题意: 给出n个数,求出去掉第i个数之后所有数的中位数,保证n是偶数. \(n\le 200000\) 分析: ...
- AtCoder Regular Contest 102
AtCoder Regular Contest 102 C - Triangular Relationship 题意: 给出n,k求有多少个不大于n的三元组,使其中两两数字的和都是k的倍数,数字可以重 ...
随机推荐
- zabbix 监控hp 打印机
https://share.zabbix.com/search?searchword=hp+printer&search_cat=1
- RaspberryPI 3b 技术总结(包括Linux)
安装系统,无屏幕,无网线,windows下 第一步当然是把ROM(官方系统)和刷写工具备好,TF卡一张,当然必须有读卡设备. 启动Etcher,将ROM刷入TF卡,这需要挺长一段时间,完毕后将会出现四 ...
- keepalive + nginx 搭建高可用集群动态网站
环境准备: 两台节点部署keepalived,并且设为互为主从,实现高可用. 两台从节点部署nginx以及相关组件,作为真实服务器实现动态网站上线. 一.MASTER(BACKUP)节点下载keepa ...
- Excel公式的常见错误值及其解决方法
Excel公式的常见错误值及其解决方法 经常用Excel的朋友可能都会遇到一些莫名奇妙的错误值信息:# N/A!.#VALUE!.#DIV/O!等等,出现这些错误的原因有很多种,如果公式不能计算正确结 ...
- .net 部署到服务端IIS,Process调用exe程序无法运行问题解决
场景: 开发某一功能将html内容转换为pdf,采用第三方插件wkhtmltopdf.exe进行转换.在本地调试正常运行,部署到服务端后文件没有正常生成. IIS中,Process打不开cmd程序,程 ...
- 如何面对这个残酷的世界?——Java模拟
1,问题引入: 房间里有100个人,每人都有100元钱,他们在玩一个游戏.每轮游戏中,每个人都要拿出一元钱随机给另一个人,最后这100个人的财富分布是怎样的? 2,问题思考: 今天有幸看到这道题目,起 ...
- python-应用OpenCV和Python进行SIFT算法的实现
如下图为进行测试的q和h,分别验证基于BFmatcher.FlannBasedMatcher等的SIFT算法 代码如下: import numpy as np import cv2 from matp ...
- 使用Inception-v3进行图像分类
https://blog.csdn.net/sinat_27382047/article/details/80534234 https://www.jianshu.com/p/cc830a6ed54b ...
- 应用安全 - 工具 - 知道创宇 - CEYE检测平台
DNS Query
- 应用安全 - 中间件漏洞 - Nostromo
CVE-2011-0751 Date: 2011.3 类型: 路径遍历 PoC:https://nvd.nist.gov/vuln/detail/CVE-2011-0751 CVE-2019-162 ...