CF#574E. OpenStreetMap 题解
中文版戳这里(来自洛谷)
做法很简单
两层单调队列
不知道deque的
就自行baidu啦,也可以参考我以前发的deque模板
上代码了
#include<bits/stdc++.h> using namespace std; const int MAX=3050; int n,m,a,b,x,y,z; long long g[9000050],h[MAX][MAX]; long long minn[MAX][MAX]; int main() { cin>>n>>m>>a>>b; cin>>g[0]>>x>>y>>z; for(int i=1;i<=n*m;i++) g[i]=(g[i-1]*x+y)%z; for(int i=1;i<=n;i++) for(int j=1;j<=m;j++) h[i][j]=g[(i-1)*m+j-1]; for(int i=1;i<=n;i++) { deque<int> dq; for(int j=1;j<=m;j++) { while(!dq.empty() && h[i][j]<=h[i][dq.back()]) dq.pop_back(); dq.push_back(j); if(!dq.empty() && j-dq.front()+1>b) dq.pop_front(); minn[i][j]=h[i][dq.front()]; } } long long ans=0; for(int j=1;j<=m;j++) { deque<int> dq; for(int i=1;i<=n;i++) { while(!dq.empty() && minn[i][j]<=minn[dq.back()][j]) dq.pop_back(); dq.push_back(i); while(!dq.empty() && i-dq.front()+1>a) dq.pop_front(); if(i>=a && j>=b) ans+=(long long)minn[dq.front()][j]; } } cout<<ans; return 0; }