description
司令部的將軍們打算在n*m的網格地圖上部署他們的炮兵部隊。乙個n*m的地圖由n行m列組成,地圖的每一格可能是山地(用"h" 表示),也可能是平原(用"p"表示),如下圖。在每一格平原地形上最多可以布置一支炮兵部隊(山地上不能夠部署炮兵部隊);一支炮兵部隊在地圖上的攻擊範圍如圖中黑色區域所示:
如果在地圖中的灰色所標識的平原上部署一支炮兵部隊,則圖中的黑色的網格表示它能夠攻擊到的區域:沿橫向左右各兩格,沿縱向上下各兩格。圖上其它白色網格均攻擊不到。從圖上可見炮兵的攻擊範圍不受地形的影響。
現在,將軍們規劃如何部署炮兵部隊,在防止誤傷的前提下(保證任何兩支炮兵部隊之間不能互相攻擊,即任何一支炮兵部隊都不在其他支炮兵部隊的攻擊範圍內),在整個地圖區域內最多能夠擺放多少我軍的炮兵部隊。
input
第一行包含兩個由空格分割開的正整數,分別表示n和m;
接下來的n行,每一行含有連續的m個字元('p'或者'h'),中間沒有空格。按順序表示地圖中每一行的資料。n <= 100;m <= 10。
output
僅一行,包含乙個整數k,表示最多能擺放的炮兵部隊的數量。
sample input
5 4sample outputphpp
pphh
pppp
phpp
phhp
6思路:首先把所有合法狀態預處理出來,可知1<<10內最多有60種合法狀態,用d[i][j][k]表示第i行狀態為j,第i-1行狀態為k時的最大值,即遍歷i-2行狀態,找到i,i-1行狀態確定時其最大值,狀態轉移方程為dp[i][j][k]=max(dp[i][j][k],dp[i-1][k][t]+sum[j]),sum[j]為j狀態時1的數量
這個找bug找了一天,才發現預處理第一行時dp[1][i][0]寫為dp[1][0][i]了,以後找不出bug時,可以把所有狀態值都列印出來,不管狀態之間轉移關係,直接手算每個狀態的對應值,看看是否正確。
#include #include #include #include #include #include #include #include #include #include #define ll long long
#define eps 1e-8
#define maxn 150
#define mod 110119
#define inf 0x3f3f3f3f
#define in freopen("in.txt","r",stdin);
using namespace std;
int n,m;
int map[105];
int cnt=0;
int str[105];
int sum[105];
int dp[105][65][65];
bool ok(int x)
void init()
sum[i]=num;//第i個狀態對應的 1的數量
} }int main(){
// in;
cin>>n>>m;
init();
memset(dp,0,sizeof(dp));
memset(map,0,sizeof(map));
char c;
for(int i=0;i>c;
if(c=='h'){
map[i+1]|=1<
題解 poj1185 狀壓DP
題目鏈結 思路摘抄自大佬部落格 按層數來dp,如果用 dp i j k 來表示在第 i 行,狀態為 j i 1行狀態為 k 時的狀態,那麼有轉移方程 dp i j k max dp i j k dp i 1 k l num i 列舉 i 層數 j 當前層狀態 k 上一層狀態 l 上上層狀態 就可以來...
POJ 1185 經典狀壓dp
做了很久的題 有注釋 include include include include includeusing namespace std int dp 107 107 107 二維記錄上一次 三維記錄此次 dp i k j max dp i k j dp i 1 t k num j t為列舉數且滿...
POJ 1185 經典狀壓dp (模板)
炮兵陣地 time limit 2000ms memory limit 65536k total submissions 26096 accepted 10072 description 司令部的將軍們打算在n m的網格地圖上部署他們的炮兵部隊。乙個n m的地圖由n行m列組成,地圖的每一格可能是山地...