[IOI1998]Polygon
很早就看到这题了...但因为有个IOI标志,拖到现在才做
由于是以前在书上看到的,就没有想过其他算法,直接区间DP了...
方程式也挺好想的
跟我们平时做数学题求几个数乘积最大差不多
最大的*最大的
最小的*最小的(可能是负数)
这样两种情况
由于求最大中要用到最小值,我们在维护最大同时维护最小
最小的*最小的
最小的*最大的
也是两种情况
再考虑加法
最大:最大+最大
最小:最小+最小
各有一种情况
Tip 上面所述的类似于最大*最大都是左区间最大/小 和右区间最大/小
表达起来大概是这样的
for(int len=2;len<=n;++len){
for(int i=1;i+len-1<=2*n;++i){
int j=i+len-1;
for(int k=i;k<j;++k){
if(opt[k+1]=='x')
cmax(dpd[i][j],dpd[i][k]*dpd[k+1][j],dpx[i][k]*dpx[k+1][j]),
cmin(dpx[i][j],dpd[i][k]*dpx[k+1][j],dpx[i][k]*dpd[k+1][j],dpx[i][k]*dpx[k+1][j]);
else
cmin(dpx[i][j],dpx[i][k]+dpx[k+1][j]),
cmax(dpd[i][j],dpd[i][k]+dpd[k+1][j]);
}
}
}
最后的代码
#include<cstdio>
#include<iostream>
#include<cstring>
#define inf (0x7fffffff)
#define writeln(x) write(x),puts("")
#define writep(x) write(x),putchar(' ')
using namespace std;
inline int read(){
int ans=0,f=1;char chr=getchar();
while(!isdigit(chr)){if(chr=='-') f=-1;chr=getchar();}
while(isdigit(chr)){ans=(ans<<3)+(ans<<1)+chr-48;chr=getchar();}
return ans*f;
}void write(int x){
if(x<0) putchar('-'),x=-x;
if(x>9) write(x/10);
putchar(x%10+'0');
}int n,a[155],dpx[155][155],dpd[155][155],ans=-inf;char opt[55];
inline void cmin(int &a,int b){if(b<a) a=b;}
inline void cmin(int &a,int b,int c){cmin(a,b),cmin(a,c);}
inline void cmin(int &a,int b,int c,int d){cmin(a,b,c),cmin(a,d);}
inline void cmax(int &a,int b){if(a<b)a=b;}
inline void cmax(int &a,int b,int c){cmax(a,b),cmax(a,c);}
int main(){
n=read();
for(register int i=1;i<=n;++i) cin>>opt[i]>>a[i];
for(register int i=1;i<=n;++i) opt[i+n]=opt[i],a[i+n]=a[i];
for(int i=1;i<=n*2;++i)
for(int j=1;j<=n*2;++j)
(i==j)?(dpx[i][i]=dpd[i][i]=a[i]):(dpd[i][j]=-inf,dpx[i][j]=inf);
for(int len=2;len<=n;++len){
for(int i=1;i+len-1<=2*n;++i){
int j=i+len-1;
for(int k=i;k<j;++k){
if(opt[k+1]=='x')
cmax(dpd[i][j],dpd[i][k]*dpd[k+1][j],dpx[i][k]*dpx[k+1][j]),
cmin(dpx[i][j],dpd[i][k]*dpx[k+1][j],dpx[i][k]*dpd[k+1][j],dpx[i][k]*dpx[k+1][j]);
else
cmin(dpx[i][j],dpx[i][k]+dpx[k+1][j]),
cmax(dpd[i][j],dpd[i][k]+dpd[k+1][j]);
}
}
}
for(int i=1;i<=n;++i) cmax(ans,dpd[i][i+n-1]);writeln(ans);
for(int i=1;i<=n;i++) if(dpd[i][i+n-1]==ans) writep(i);
return 0;
}
[IOI1998]Polygon的更多相关文章
- IOI1998 Polygon [区间dp]
[IOI1998]Polygon 题意翻译 题目可能有些许修改,但大意一致 多边形是一个玩家在一个有n个顶点的多边形上的游戏,如图所示,其中n=4.每个顶点用整数标记,每个边用符号+(加)或符号*(乘 ...
- [IOI1998]Polygon(区间dp)
[IOI1998]Polygon 题意翻译 多边形是一个玩家在一个有n个顶点的多边形上的游戏,如图所示,其中n=4.每个顶点用整数标记,每个边用符号+(加)或符号*(乘积)标记. 第一步,删除其中一条 ...
- POJ 1179 IOI1998 Polygon
Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 5472 Accepted: 2334 Description Polyg ...
- 【洛谷P4342】[IOI1998]Polygon
Polygon 比较裸的环形DP(也可以说是区间DP) 将环拆成链,复制到后面,做区间DP即可 #include<iostream> #include<cstdio> usin ...
- P4342 [IOI1998]Polygon
题意翻译 题目可能有些许修改,但大意一致 多边形是一个玩家在一个有n个顶点的多边形上的游戏,如图所示,其中n=4.每个顶点用整数标记,每个边用符号+(加)或符号*(乘积)标记. 第一步,删除其中一条边 ...
- luogu P4342 [IOI1998]Polygon
IOI早期这么多dp? 题目要求断掉环上的一边,我们可以断环为链,开两倍数组 容易想到dp,设\(f_{i,j}\)为区间\([i,j]\)的最大值,然后就是个枚举断点的区间dp 不过可能会有负数出现 ...
- 【洛谷 P4342】[IOI1998]Polygon(DP)
题目链接 题意不再赘述. 这题和合并石子很类似,但是多了个乘法,而乘法是不满足"大大得大"的,因为两个非常小的负数乘起来也会很大,一个负数乘一个很大的整数会很小,所以我们需要添加一 ...
- 洛谷 P4342 [IOI1998]Polygon
题目传送门 解题思路: 一道环形dp,只不过有个地方要注意,因为有乘法,两个负数相乘是正数,所以最小的数是负数,乘起来可能比最大值大,所以要记录最小值(这道题是紫题的原因). AC代码: #inclu ...
- [IOI1998] Polygon (区间dp,和石子合并很相似)
题意: 给你一个多边形(可以看作n个顶点,n-1条边的图),每一条边上有一个符号(+号或者*号),这个多边形有n个顶点,每一个顶点有一个值 最初你可以把一条边删除掉,这个时候这就是一个n个顶点,n-2 ...
随机推荐
- [luoguP1021] 邮票面值设计(DFS + dp)
传送门 数据很小,可以DFS,判断的时候用背包DP 然而不知到枚举到哪里.... 首先枚举前可以求一遍题目中的MAX,下一层DFS的时候可以只枚举到MAX + 1,因为再往上就必定会出现断层 蒟蒻很菜 ...
- Linux下汇编语言学习笔记66 ---
这是17年暑假学习Linux汇编语言的笔记记录,参考书目为清华大学出版社 Jeff Duntemann著 梁晓辉译<汇编语言基于Linux环境>的书,喜欢看原版书的同学可以看<Ass ...
- Linux下汇编语言学习笔记64 ---
这是17年暑假学习Linux汇编语言的笔记记录,参考书目为清华大学出版社 Jeff Duntemann著 梁晓辉译<汇编语言基于Linux环境>的书,喜欢看原版书的同学可以看<Ass ...
- Thinkphp5.0 的使用模型Model查询
Thinkphp5.0 的使用模型Model查询 一.查询多条记录 获取多个数据可以使用:select()方法和all()方法. 示例一:使用all()方法. //(1)筛选条件使用闭包函数 $res ...
- 在springBoot与quartz 整合中 @Transaction 失效
问题1::springBoot在与quartz 整合时,使用@Transaction 注解时事务失效 解决方案:创建一个类使用@component被spring管理 ,使用@Transaction标识 ...
- 【SQL Server 学习系列】-- 清除SQL Server 2012连接过的服务器名称
需要删除两个地方,删除前请注意备份! 1. %AppData%\Microsoft\Microsoft SQL Server\100\Tools\Shell\SqlStudio.bin 2. %A ...
- JFileChooser 中文API
javax.swing类 JFileChooser java.lang.Object java.awt.Component java.awt.Container javax.swing.JCompon ...
- 在Windows上安装Nexus
在Windows上安装Nexus 学习了:https://www.cnblogs.com/yucongblog/p/6696736.html 下载地址:https://sonatype-downloa ...
- php 获取今天,本周,本月,三个月内,半年内,今年的开始和结束时间
$now = time(); //今天 $today_audit_num = 0; $today_use_num = 0; $beginTim ...
- 修改mysql root密码
mysql密码丢失后,在mysql命令行下执行如下命令,即可将root用户密码清空: mysqld_safe --skip-grant-tables& mysql修改密码 mysql修改,可在 ...