Acwing-283-多边形(区间DP)
链接:
https://www.acwing.com/problem/content/285/
题意:
“多边形游戏”是一款单人益智游戏。
游戏开始时,给定玩家一个具有N个顶点N条边(编号1-N)的多边形,如图1所示,其中N = 4。
每个顶点上写有一个整数,每个边上标有一个运算符+(加号)或运算符*(乘号)。
1179_1.jpg
第一步,玩家选择一条边,将它删除。
接下来在进行N-1步,在每一步中,玩家选择一条边,把这条边以及该边连接的两个顶点用一个新的顶点代替,新顶点上的整数值等于删去的两个顶点上的数按照删去的边上标有的符号进行计算得到的结果。
下面是用图1给出的四边形进行游戏的全过程。
1179_2.jpg
最终,游戏仅剩一个顶点,顶点上的数值就是玩家的得分,上图玩家得分为0。
请计算对于给定的N边形,玩家最高能获得多少分,以及第一步有哪些策略可以使玩家获得最高得分。
思路:
先处理环, 将环变成链式再扩大两倍,就可以处理环了,从l-(l+n-1)的范围就是将l前面的边在第一步断开的情况.
考虑步数, 对两个堆进行dp, 操作受到符号限制.
代码:
#include <bits/stdc++.h>
using namespace std;
const int INF = 1e9;
const int NINF = -1e9;
int a[110], op[110];
int Dp[110][110][2];
int n;
char ope;
int main()
{
scanf("%d", &n);
getchar();
for (int i = 1;i <= n;i++)
{
scanf("%c%d", &ope, &a[i]);
getchar();
// cout << ope << endl;
if (ope == 't')
op[i] = 1;
else
op[i] = 0;
}
for (int i = n+1;i <= 2*n;i++)
{
a[i] = a[i-n];
op[i] = op[i-n];
}
for (int i = 1;i <= 2*n;i++)
{
for (int j = 1;j <= 2*n;j++)
{
Dp[i][j][0] = NINF, Dp[i][j][1] = INF;
if (i == j)
Dp[i][j][0] = Dp[i][j][1] = a[i];
}
}
// for (int i = 1;i <= 2*n;i++)
// cout << op[i] << ' ' << a[i] << ' ' ;
// cout << endl;
for (int len = 2;len <= n;len++)
{
for (int l = 1;l <= 2*n-len+1;l++)
{
int r = l+len-1;
for (int k = l;k < r;k++)
{
if (op[k+1] == 1)
{
Dp[l][r][0] = max(Dp[l][r][0], Dp[l][k][0]+Dp[k+1][r][0]);
Dp[l][r][1] = min(Dp[l][r][1], Dp[l][k][1]+Dp[k+1][r][1]);
}
else
{
Dp[l][r][0] = max(Dp[l][r][0], Dp[l][k][0]*Dp[k+1][r][0]);
// Dp[l][r][0] = max(Dp[l][r][0], Dp[l][k][0]+Dp[k+1][r][0]);
Dp[l][r][0] = max(Dp[l][r][0], Dp[l][k][1]*Dp[k+1][r][1]);
Dp[l][r][0] = max(Dp[l][r][0], Dp[l][k][1]*Dp[k+1][r][0]);
Dp[l][r][0] = max(Dp[l][r][0], Dp[l][k][0]*Dp[k+1][r][1]);
Dp[l][r][1] = min(Dp[l][r][1], Dp[l][k][1]*Dp[k+1][r][1]);
// Dp[l][r][1] = min(Dp[l][r][1], Dp[l][k][1]+Dp[k+1][r][1]);
Dp[l][r][1] = min(Dp[l][r][1], Dp[l][k][0]*Dp[k+1][r][0]);
Dp[l][r][1] = min(Dp[l][r][1], Dp[l][k][1]*Dp[k+1][r][0]);
Dp[l][r][1] = min(Dp[l][r][1], Dp[l][k][0]*Dp[k+1][r][1]);
}
}
}
}
int ans = NINF;
for (int l = 1;l <= n+1;l++)
{
int r = l+n-1;
// cout << Dp[l][r][0] << endl;
ans = max(ans, Dp[l][r][0]);
}
set<int> st;
for (int l = 1;l <= n;l++)
{
int r = l+n-1;
if (Dp[l][r][0] == ans)
st.insert(l);
}
printf("%d\n", ans);
for (auto x: st)
printf("%d ", x);
puts("");
return 0;
}
/*
3
t 1 t 1 x 1
*/
Acwing-283-多边形(区间DP)的更多相关文章
- 多边形——————区间dp
原题链接:https://www.acwing.com/problem/content/285/ 题意简单来说就是:给你一个环,断掉一条边使其成为一个链,用这个链跑dp,求最大得分. 首先这不是一道板 ...
- poj1179多边形——区间DP
题目:http://poj.org/problem?id=1179 区间DP,值得注意的是有负值,而且有乘法,因此可能会影响最大值: 注意memset中写-1仅仅是-1,-2才是一个很小的负数: 最后 ...
- Hzoi 2018.2.11多边形 区间DP
给定一个由N个顶点构成的多边形,每个顶点被赋予一个整数值,而每条边则被赋予一个符号:+(加法运算)或者*(乘法运算),所有边依次用整数1到N标识. 一个多边形的图形表示 首次移动,允许将某条边删除: ...
- Vijos 1565 多边形 【区间DP】
描述 zgx给了你一个n边的多边形,这个多边形每个顶点赋予一个值,每条边都被标上运算符号+或*,对于这个多边形有一个游戏,游戏的步骤如下:(1)第一步,删掉一条边:(2)接下来n-1步,每步对剩下的边 ...
- 多边形游戏——区间dp
题目描述 多边形(Polygon)游戏是单人玩的游戏,开始的时候给定一个由N个顶点构成的多边形(图1所示的例子中,N=4),每个顶点被赋予一个整数值,而每条边则被赋予一个符号:+(加法运算)或者*(乘 ...
- kuangbin 区间dp
A - Cake 题目大意:给你一个n个顶点(n<=100)的多边形和每两个点连边的消耗,让你求把这个多边形全部切成三角形所需要的最小消耗,如果这个多边形为凹多边形则输出无解. 思路:先求一个凸 ...
- BZOJ 1719--[Usaco2006 Jan] Roping the Field 麦田巨画(几何&区间dp)
1719: [Usaco2006 Jan] Roping the Field 麦田巨画 Time Limit: 5 Sec Memory Limit: 64 MBSubmit: 82 Solved ...
- 区间DP小结
也写了好几天的区间DP了,这里稍微总结一下(感觉还是不怎么会啊!). 但是多多少少也有了点感悟: 一.在有了一点思路之后,一定要先确定好dp数组的含义,不要模糊不清地就去写状态转移方程. 二.还么想好 ...
- ZOJ 3537 Cake(凸包+区间DP)
题目链接:http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3537 题目大意:给出一些点表示多边形顶点的位置,如果不是凸多边形 ...
- ZOJ 3537 Cake 求凸包 区间DP
题意:给出一些点表示多边形顶点的位置(如果多边形是凹多边形就不能切),切多边形时每次只能在顶点和顶点间切,每切一次都有相应的代价.现在已经给出计算代价的公式,问把多边形切成最多个不相交三角形的最小代价 ...
随机推荐
- jvm的学习笔记:二、类的初始化,代码实战(1)
对于静态字段来说,直接定义该字段的类才会被初始化 System.out.println(MyChild1.str); 输出: myParent1 static block hello myParent ...
- Pytorch修改ResNet模型全连接层进行直接训练
之前在用预训练的ResNet的模型进行迁移训练时,是固定除最后一层的前面层权重,然后把全连接层输出改为自己需要的数目,进行最后一层的训练,那么现在假如想要只是把 最后一层的输出改一下,不需要加载前面层 ...
- 【Python开发】使用pyplot模块绘图
快速绘图 使用pyplot模块绘图¶ matplotlib的pyplot模块提供了和MATLAB类似的绘图API,方便用户快速绘制二维图表.我们先看一个简单的例子: 05-matplotlib/mat ...
- 【VS开发】CTime和CTimeSpan使用
此文就用一个程序表示,相信只要是学过C语言的都能看得懂的. [html] view plain copy print? // CTimeTest.cpp : Defines the entry poi ...
- java文件操作解析
转载:http://blog.csdn.net/cynhafa/article/details/6882061 字节流与和字符流的使用非常相似,两者除了操作代码上的不同之外,是否还有其他的不同呢? 实 ...
- 统计sql server 2012表的行数
--功能:统计sql server 2012表的行数 SELECT a.name, a.object_id, b.rows, b.index_id FROM sys.tables AS a INNER ...
- 2019.07.05 纪中_B
今日膜拜:czj大佬orz%%% 2019.07.05[NOIP提高组]模拟 B 组 今天做题的时候大概能判断出题人的考点,可是就是没学过...特别痛苦 T0:栈的定义,模拟就好了T1:感觉像是找规律 ...
- 300英雄的危机(heroes)
题面 正解与图书馆馆长的考验一致,都是分层图SPFA: #include <iostream> #include <cstdio> #include <cstring&g ...
- AppCan模拟器调试
来源: 1, 页面CSS调试 2, JS调试 3, 插件请打包后手机调试 4, 打开另一个页面示例: appcan.button("#myBtn", "ani-uct&q ...
- 5表联查yii框架权限控制
一:控制器部分 <?php namespace app\controllers; use yii\web\Controller; class PreController extends Cont ...