Wannafly挑戰賽21 C 大水題

2021-08-22 11:34:46 字數 1335 閱讀 7216

題目描述

現在給你n個正整數ai,每個數給出一「好數程度」 gi(數值相同但位置不同的數之間可能有不同的好數程度)。對於在 i 位置的數,如果有一在j位置的數滿足 j < i 且 ai=aj,則你可以將位於[i,j]閉區間內的序列評為「好序列」,然後獲得∑gk(j≤k≤i)(此閉區間內「好數程度」之和)分數。

注意: 在所有情況下,每個數都只能被乙個」好序列」包含(只能與其他相應數被評為」好序列」一次);在符合要求的情況下,」好序列」的評定次數不受限制,且通過不同」好序列」獲得的分數可以累加。

輸入描述:

第一行有乙個正整數n。

接下來的一行有n個正整數ai,表示意義如上。

(保證ai在32位整型範圍內)

接下來的一行有n個正整數gi,表示ai的」好數程度」。

(保證gi在64位整型範圍內)

輸出描述:

乙個整數,你可以獲得的最大分數(通過不同」好序列」獲得的分數可以累加),保證答案在64位整型範圍內。

示例1輸入7

1 2 1 2 3 2 3

1 4 3 4 3 4 5

輸出23

備註:

資料範圍 2≤n≤300000

區間dp,但是常規區間dp方程式是列舉所有子區間

for (int len = 1; len < n; len++) 

}}

dp[i]=max(dp[j-1]+sum(j~i))a[j]==a[i];

會超時,記錄相同數字的最優點

詳細看**:

#include#include#includeconst int maxn=300000+10;

typedef long long ll;

using namespace std;

mapp;

int a[maxn],best[maxn],last[maxn];

ll dp[maxn],sum[maxn];

int main()else }

int lin;

for(int i=1;i<=n;i++)

ll ans=0;

for(int i=1;i<=n;i++) //比如資料裡有3個2,就會比較前面那個2好一點,等到下次再遇到2時,再比較,但是

//每次只用比較前面那個2和最好的那個2就行

} ans=max(ans,dp[i]);

} printf("%lld\n",ans);

return 0;

}

Wannafly挑戰賽21 C 大水題

題目描述 現在給你n個正整數ai,每個數給出一 好數程度 gi 數值相同但位置不同的數之間可能有不同的好數程度 對於在 i 位置的數,如果有一在j位置的數滿足 j i 且 ai aj,則你可以將位於 i,j 閉區間內的序列評為 好序列 然後獲得 gk j k i 此閉區間內 好數程度 之和 分數。注...

Wannafly挑戰賽21 大水題 DP

時間限制 c c 1秒,其他語言2秒 空間限制 c c 131072k,其他語言262144k 64bit io format lld 題目描述 現在給你n個正整數ai,每個數給出一 好數程度 gi 數值相同但位置不同的數之間可能有不同的好數程度 對於在 i 位置的數,如果有一在j位置的數滿足 j ...

Wannafly挑戰賽A 概率DP

給你乙個長 n 的序列,m 次查詢 每次查詢給乙個 x,然後 從序列的最左端 1 開始,每次隨機的選擇乙個右端點 r,如果兩個端點間的區間和不超過 x 就進行一次分割,然後把左端點變成 r 1,否則一直隨機下去。問這樣分割出來的期望段數 第一行兩個數 n,m 之後一行 n 個數表示這個序列 之後m行...