洛谷 題解 P1133 教主的花園

2022-02-13 23:23:29 字數 1406 閱讀 3773

$n<=10^5 $

o(n)演算法

dp[i][j][k]表示在第i個位置,種j*10的高度的樹,且這棵樹是否比相鄰兩棵樹高
dp[i][1][0]=max(dp[i-1][2][1],dp[i-1][3][1])+a[i];

//種高度為10的樹,肯定比相鄰的兩棵樹矮

dp[i][2][0]=dp[i-1][3][1]+b[i];

//種高度為20且高度比相鄰的矮的,那麼第i-1棵肯定是高度為30且比相鄰的兩棵高的

dp[i][2][1]=dp[i-1][1][0]+b[i];

//種高度為20且高度比相鄰的高的,那麼第i-1棵肯定是高度為10且比相鄰的兩棵矮的

dp[i][3][1]=max(dp[i-1][1][0],dp[i-1][2][0])+c[i];

//種高度為30的樹,肯定比相鄰的兩棵樹高

取dp[n][1][0]、dp[n][2][0]、dp[n][2][1]、dp[n][3][1]的最大值
但是只有70分...

特別地,第1個位置的樹與第n個位置的樹相鄰。

這個好像沒有考慮過

所以要把位置為1的特殊處理

dp[1][1][0]=max(dp[n][2][1],dp[n][3][1])+a[1];

dp[1][2][0]=dp[n][3][1]+b[1];

dp[1][2][1]=dp[n][1][0]+b[1];

dp[1][3][1]=max(dp[n][1][0],dp[n][2][0])+c[1];

那麼答案就應該是這個:

取dp[1][1][0]、dp[1][2][0]、dp[1][2][1]、dp[1][3][1]的最大值
完整**:

#includeusing namespace std;

const int maxn=100000+10;

int n;

int a[maxn],b[maxn],c[maxn];

int dp[maxn][4][2];

inline int read()

return tot;

}int main()

dp[1][1][0]=max(dp[n][2][1],dp[n][3][1])+a[1];

dp[1][2][0]=dp[n][3][1]+b[1];

dp[1][2][1]=dp[n][1][0]+b[1];

dp[1][3][1]=max(dp[n][1][0],dp[n][2][0])+c[1];

cout

}

洛谷 P1133 教主的花園 題解

通往題目的大門 進入正題,需要求最大觀賞價值,那麼用於dp的f陣列首先肯定要有兩維,第一維i表示第i個位置,第二維j表示種第j種樹 我們不妨設10,20,30這三種樹為1,2,3 然後又發現,第i個位置能種什麼樹,不單單跟上乙個位置有關,還跟上上個位置有關,那這樣呼叫兩位去dp顯得十分複雜,於是我們...

洛谷 P1133 教主的花園

教主有著乙個環形的花園,他想在花園周圍均勻地種上n棵樹,但是教主花園的土壤很特別,每個位置適合種的樹都不一樣,一些樹可能會因為不適合這個位置的土壤而損失觀賞價值。教主最喜歡3種樹,這3種樹的高度分別為10,20,30。教主希望這一圈樹種得有層次感,所以任何乙個位置的樹要比它相鄰的兩棵樹的高度都高或者...

dp 洛谷P1133 教主的花園

一開始題目看錯了,以為很水的 然後0 爆蛋之後開始想標算 想了半天就是不知道怎麼處理這個環 設f i j k 表示第i行第j列的答案 k 0表示前面比他小 k 1表示前面比他大 但是這樣我們第一位要靠第n位來更新 那我們直接不更新第一位 從第二位來,然後跑完後把n位和1位結合一下就好了 includ...