单调队列优化dp20pts求调,玄关
查看原帖
单调队列优化dp20pts求调,玄关
511811
崛起的滑稽楼主2024/7/10 16:39

双端队列类应该没啥问题,换deque也一个分 所以从分割线开始看吧(

#include <bits/stdc++.h>
#define int __int128
using namespace std;
namespace LYH{
	template<typename T>inline void input(T &x){
		char c='?';
		bool flag=false;//正负
		x=0;
		while(c=getchar(),!isdigit(c)){
			if(c=='-'){
				flag=true;
			}
		}
		while(isdigit(c)){
			x=x*10+(c-'0');
			c=getchar();
		}
		if(flag){
			x=-x;
		}
	}
	template<typename T>inline void print(T x){
		if(x<0){
			x=-x;
			putchar('-');
		}
		if(x>9){
			print(x/10);
		}
		putchar(char(x%10+'0'));
	}
	class double_queue
	{
	public:
		void pop_front()
		{
			if(head<=tail)
				++head;
		}
		void pop_back()
		{
			if (head <= tail)
			{
				q.pop_back();
				--tail;
			}
		}
		void push_back(int value)
		{
			q.push_back(value);
			++tail;
		}
		void push_front(int value){
			if(head){
				++tail;
				q.insert(q.begin(),value);
				return;
			}
			q[--tail]=value;
		}
		void clear()
		{
			q.clear();
			head=0;
			tail=-1;
		}
		bool empty(){return !(head<=tail);}
		int front() { return q[head]; }
		int back() { return q[tail]; }
		int begin() { return head; }
		int end() { return tail; }
		std::vector<int>::iterator beginP() { return q.begin(); }
		std::vector<int>::iterator endP(){ return q.end(); }
	private:
		std::vector<int> q;
		int head = 0, tail = -1;
		
	};
}
//______________________________分割线____________________________以下为有效代码
const int MAXN=1e6+10;
int n,k,a,dp[MAXN],s[MAXN],ds[MAXN];
LYH::double_queue q;
signed main(){
	LYH::input(n);
	LYH::input(k);
	q.push_back(0);
	for(int i=1;i<=n;++i){
		LYH::input(a);
		s[i]=s[i-1]+a;
		ds[i]=dp[i-1]-s[i];
		while(!q.empty()&&q.front()<i-k){
			q.pop_front();
		}
		while(!q.empty()&&dp[q.back()]<ds[i]){
			q.pop_back();
		}
		q.push_back(i);
		dp[i]=ds[q.front()]+s[i];
	}
	LYH::print(dp[n]);
}
2024/7/10 16:39
加载中...