于万人中万幸得以相逢,刹那间澈净明通,成为我所向披靡的勇气和惶恐,裂山海,堕苍穹。 |

Jason142

园龄:3年粉丝:12关注:78

P5858 「SWTR-03」Golden Sword做题笔记

开始看的时候以为是个背包,看了一眼标签,发现没有背包两个字,觉得可能是漏加上去了,但背包死活想不出思路,看了眼题解,原来是 dp 加单调队列优化,然后开始看题解,看了大半天没看懂,照着题解的框架打了一遍才半懂,大致思路是用单调队列维护炉子里的和还没进炉子里的原料的顺序?然后发现照着题解打的 35pts,找了半天才发现是最小值的初始化问题,题解里用的是 -1008600110086001,而我用的是 -0x7fffffffffffffff。后来找了某大佬,说我用的数太小容易溢出,并推荐我用 -0x3f3f3f3f3f3f3f3f,然后就过了。

#include <bits/stdc++.h>
  using namespace std;
const long long FINF=-0x3f3f3f3f3f3f3f3f; 
long long n,m,k,a,s[5005][5005],q[5005],t[5005],ans,l,r,i,j;
int main()
{
	ios::sync_with_stdio(0);
	cin.tie(0); cout.tie(0);
	cin>>n>>m>>k;
	for (i=0;i<=n;i++)
	{
		for (j=0;j<=m;j++)
		{
			s[i][j]=FINF;
		}
	}
	s[0][0]=0;
	for (i=1;i<=n;i++)
	{
		cin>>a;
		l=1;
		r=1;
		t[l]=m;
		q[l]=s[i-1][m];
		for (j=m;j>0;j--)
		{
			while (t[l]>j+k-1 && l<=r) l++;
			while (q[r]<s[i-1][j-1] && l<=r) r--;
			t[++r]=j-1;
			q[r]=s[i-1][j-1];
			s[i][j]=q[l]+j*a;
		}
	}
	ans=FINF;
	for (i=0;i<=m;i++)
	{
		ans=max(ans,s[n][i]);
	}
	cout<<ans<<endl;
	return 0;
}

本文作者:Jason142

本文链接:https://www.cnblogs.com/Jason142/p/16271766.html

版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。

posted @   Jason142  阅读(48)  评论(0编辑  收藏  举报
点击右上角即可分享
微信分享提示
评论
收藏
关注
推荐
深色
回顶
收起