1. 程式人生 > >[NOI2005]瑰麗華爾茲_動態規劃_單調佇列

[NOI2005]瑰麗華爾茲_動態規劃_單調佇列

Code:

#include<cstdio>
#include<cstring>
#include<deque>
#include<algorithm>
using namespace std;
const int N = 200 + 3;
char map[N][N];
int n, m, k, dp[N][N], fin;
struct Node{ 
    int x, y, val;
    Node(int x = 0, int y = 0,int val = 0): x(x), y(y), val(val){}
};
deque<Node>
Q; inline void erase_q(){ while(!Q.empty()) Q.pop_front();} inline int dist(int a,int b, int c,int d){ return abs(a - c) + abs(b- d);} inline void solve(int y,int x,int d,int len,int h) { erase_q(); Q.push_back(Node(x, y, dp[x][y])); for(int i = 1;i < h; ++i) { if(d == 1) --
y; if(d == 2) ++y; if(d == 3) --x; if(d == 4) ++x; if(map[y][x] == 'x'){ erase_q(); continue; } while(!Q.empty() && dist(Q.front().x, Q.front().y , x , y) > len) Q.pop_front(); while(!Q.empty() && dist(Q.back(). x, Q.back(). y, x , y) + Q.back().val <=
dp[x][y]) Q.pop_back(); Q.push_back(Node(x , y, dp[x][y])); dp[x][y] = dist(Q.front(). x , Q.front().y, x , y) + Q.front().val; fin = max(fin, dp[x][y]); } } int main() { memset(dp, -0x3f, sizeof(dp)); int x, y; scanf("%d%d%d%d%d",&n,&m,&x,&y,&k); dp[y][x] = 0; for(int i = 1;i <= n; ++i) scanf("%s",map[i] + 1); for(int i = 1;i <= k; ++i) { int s, t, d; scanf("%d%d%d",&s,&t,&d); if(d == 1) for(int i = 1;i <= m; ++i) solve(n, i, d, t - s + 1, n); if(d == 2) for(int i = 1;i <= m; ++i) solve(1, i, d, t - s + 1, n); if(d == 3) for(int i = 1;i <= n; ++i) solve(i, m, d, t - s + 1, m); if(d == 4) for(int i = 1;i <= n; ++i) solve(i, 1, d, t - s + 1, m); } printf("%d",fin); return 0; }