bzoj 1499: [NOI2005]瑰丽华尔兹【dp+单调队列】
设f[a][i][j]为第a段时间结束时在(i,j)位置的最长滑行距离,转移很好想,就是分四个方向讨论,然后枚举这段时间的滑行长度取个max即可
但是这样是O(n^4)的,考虑优化
发现同一行或列,取max对应a-1中的是单调挪动的一个区间,所以用单调栈维护当前区间,每次移动的时候要把左端点已经大于最长滑行距离的出队,然后把新点放进去,然后直接更新答案,这样就省去了一个n的时间
注意如果遇到障碍的话,当前的f赋值-inf,然后把队列清空
#include<iostream>
#include<cstdio>
using namespace std;
const int N=205,dx[]={0,-1,1,0,0},dy[]={0,0,0,-1,1},inf=1e9;
int n,m,k,sx,sy,s[N],t[N],d[N],f[N][N][N],q[N],l,r,ans;
char c[N][N];
int main()
{
scanf("%d%d%d%d%d",&n,&m,&sx,&sy,&k);
for(int i=1;i<=n;i++)
scanf("%s",c[i]+1);
for(int i=1;i<=k;i++)
scanf("%d%d%d",&s[i],&t[i],&d[i]);
for(int i=1;i<=n;i++)
for(int j=1;j<=m;j++)
f[0][i][j]=-inf;
f[0][sx][sy]=0;
for(int a=1;a<=k;a++)
{
if(d[a]==1)
{
for(int j=1;j<=m;j++)
{
l=1,r=0;
for(int i=n;i>=1;i--)
{
if(c[i][j]=='x')
{
l=1,r=0;
f[a][i][j]=-inf;
continue;
}
while(l<=r&&q[l]-i>t[a]-s[a]+1)
l++;
while(l<=r&&f[a-1][i][j]+i>f[a-1][q[r]][j]+q[r])
r--;
q[++r]=i;
f[a][i][j]=f[a-1][q[l]][j]+q[l]-i;
}
}
}
if(d[a]==2)
{
for(int j=1;j<=m;j++)
{
l=1,r=0;
for(int i=1;i<=n;i++)
{
if(c[i][j]=='x')
{
l=1,r=0;
f[a][i][j]=-inf;
continue;
}
while(l<=r&&i-q[l]>t[a]-s[a]+1)
l++;
while(l<=r&&f[a-1][i][j]-i>f[a-1][q[r]][j]-q[r])
r--;
q[++r]=i;
f[a][i][j]=f[a-1][q[l]][j]+i-q[l];
}
}
}
if(d[a]==3)
{
for(int i=1;i<=n;i++)
{
l=1,r=0;
for(int j=m;j>=1;j--)
{
if(c[i][j]=='x')
{
l=1,r=0;
f[a][i][j]=-inf;
continue;
}
while(l<=r&&q[l]-j>t[a]-s[a]+1)
l++;
while(l<=r&&f[a-1][i][j]+j>f[a-1][i][q[r]]+q[r])
r--;
q[++r]=j;//cerr<<i<<" "<<j<<" "<<q[l]<<" "<<f[a-1][i][j]+j<<" "<<f[a-1][i][q[l]]+q[l]<<endl;
f[a][i][j]=f[a-1][i][q[l]]+q[l]-j;
}
}
}
if(d[a]==4)
{
for(int i=1;i<=n;i++)
{
l=1,r=0;
for(int j=1;j<=m;j++)
{
if(c[i][j]=='x')
{
l=1,r=0;
f[a][i][j]=-inf;
continue;
}
while(l<=r&&j-q[l]>t[a]-s[a]+1)
l++;
while(l<=r&&f[a-1][i][j]-j>f[a-1][i][q[r]]-q[r])
r--;
q[++r]=j;//cerr<<i<<" "<<j<<" "<<q[l]<<endl;
f[a][i][j]=f[a-1][i][q[l]]+j-q[l];
}
}
}
// for(int i=1;i<=n;i++)
// {
// for(int j=1;j<=m;j++)
// cerr<<f[a][i][j]<<" ";
// cerr<<endl;
// }
// cerr<<endl;
}
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
ans=max(ans,f[k][i][j]);
printf("%d\n",ans);
return 0;
}
/*
10 10 5 8 5
..........
......xxxx
.....xxxxx
.....xxxxx
..........
xxxx......
..........
..........
..........
..x.......
1 5 3
6 7 1
8 11 2
12 15 3
16 17 2
*/
bzoj 1499: [NOI2005]瑰丽华尔兹【dp+单调队列】的更多相关文章
- BZOJ1499:[NOI2005]瑰丽华尔兹(DP,单调队列)
Description 你跳过华尔兹吗?当音乐响起,当你随着旋律滑动舞步,是不是有一种漫步仙境的惬意?众所周知,跳华尔兹时,最重要的是有好的音乐.但是很少有几个人知道,世界上最伟大的钢琴家一生都漂泊在 ...
- BZOJ 1499 [NOI2005] 瑰丽华尔兹 | 单调队列优化DP
BZOJ 1499 瑰丽华尔兹 | 单调队列优化DP 题意 有一块\(n \times m\)的矩形地面,上面有一些障碍(用'#'表示),其余的是空地(用'.'表示).每时每刻,地面都会向某个方向倾斜 ...
- bzoj 1499 [NOI2005]瑰丽华尔兹——单调队列优化dp
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1499 简单的单调队列优化dp.(然而当时却WA得不行.今天总算填了坑) 注意滚动数组赋初值应 ...
- BZOJ 1499 NOI2005 瑰丽华尔兹 单调队列
题目大意:给定一个m*n的地图,一些点有障碍物,钢琴初始在一个点,每一个时间段能够选择向给定的方向移动一段距离,求最长路径长 朴素DP的话,我们有T个时间段,每一个时间段有m*n个点,n个时间,一定会 ...
- BZOJ1499 [NOI2005]瑰丽华尔兹 【单调队列优化dp】
题目 你跳过华尔兹吗?当音乐响起,当你随着旋律滑动舞步,是不是有一种漫步仙境的惬意?众所周知,跳华尔兹时,最重要的是有好的音乐.但是很少有几个人知道,世界上最伟大的钢琴家一生都漂泊在大海上,他的名字叫 ...
- 2018.09.10 bzoj1499: [NOI2005]瑰丽华尔兹(单调队列优化dp)
传送门 单调队列优化dp好题. 这题其实很简单. 我们很容易想到一个O(T∗n∗m)" role="presentation" style="position: ...
- bzoj1499: [NOI2005]瑰丽华尔兹&&codevs1748 单调队列优化dp
这道题 网上题解还是很多很好的 强烈推荐黄学长 码风真的好看 神犇传送门 学习学习 算是道单调队列优化dp的裸题吧 #include<cstdio> #include<cstring ...
- ●BZOJ 1499 [NOI2005]瑰丽华尔兹
题链: http://www.lydsy.com/JudgeOnline/problem.php?id=1499 题解: 单调队列优化DP 定义 dp[t][x][y] 表示第t个时间段之后,处在(x ...
- 洛谷P2254 [NOI2005]瑰丽华尔兹(单调队列)
传送门 题解 大概就是设$dp[i][x][y]$表示在第$i$个时间段,在$(x,y)$时的最大滑动距离 然后转移是$dp[i][x][y]=max(dp[i-1][x][y],dp[i][x'][ ...
随机推荐
- 胜利大逃亡--hdu --1253(bfs)
Problem Description Ignatius被魔王抓走了,有一天魔王出差去了,这可是Ignatius逃亡的好机会. 魔王住在一个城堡里,城堡是一个A*B*C的立方体,可以被表示成A个B*C ...
- MySQL查询count(*)、count(1)、count(field)的区别收集
经过查询研究得出这个和MySQL中用什么引擎有关,比如InnoDB和MyISAM在处理这count(*).count(1).count(field)都有不同的方式,还有就是和版本都有关系,不同的版本会 ...
- 一起talk C栗子吧(第九十六回:C语言实例--使用共享内存进行进程间通信二)
各位看官们.大家好,上一回中咱们说的是使用共享内存进行进程间通信的样例,这一回咱们接着上一回内容继续说使用共享内存进行进程间通信. 闲话休提,言归正转.让我们一起talk C栗子吧! 我们在上一回中介 ...
- js 判断对象中所有属性是否为空
测试: var obj = {a:"123",b:""}; for(var key in obj){ if(!obj[key]) return; } 函数封装: ...
- js常用的正则表达操作
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...
- Navicat for MySQL中文破解版免费下载
不知道用过MySQL workbench数据库的朋友或站长有没有都遇到过这样的问题? 就是用ssh的连接方式连接数据库的时候,第一次可以连接的上,但是第二次就不行了,以后再用workbench就再也连 ...
- Oracle imp exp命令具体解释
怎样在oracle中导入dmp数据库文件? oracle数据导入导出imp/exp就相当于oracle数据还原与备份.exp命令能够把数据从远程数据库server导出到本地的dmp文件,imp命令能够 ...
- Filter 详解
一.Filter简介 Filter也称之为过滤器,它是Servlet技术中最激动人心的技术,WEB开发人员通过Filter技术,对web服务器管理的所有web资源:例如Jsp, Servlet, 静态 ...
- struts2的一些小问题
1.action和ValueStack的关系2.ValueStack的类set()方法和setValue()方法的区别3.ValueStack的类push()方法的作用4.从ValueStack对象中 ...
- MVC中从Controller像View层传值
MVC中的Controller不能直接的訪问View层中的控件,那么是怎样的将Controller中值传到View中,经常使用的有4种 ViewData: 是获取或设置视图的字典对象,它里面存放的是键 ...