hdu5791
dp[i][j]表示的是序列a前i個數字和序列b前j個數字的公共子串行的總個數,那麼的dp公式就可以這麼表示
理解一下此公式若最尾部的a[i]和b[j]相等的話,那麼單獨的a[i]和b[j]組成1個相同子串行。
同時我們可以想一下之前的前i-1個子序列和前j-i個子序列再加上a[i]又能組成dp[i-1]個公共子串行。
當然了,包含第i個數字的前i個序列a和前j-1個數字的序列b以及包含第j個數字的前j個序列b和前i-1個數字的序列a也要算上。
所以把上面3種情況一合併就是前i-1個子序列a和前j個子序列b的公共子串行個數加上前i個子序列a和前j-1個子序列b的公共子串行個數再加1。
這裡包含了2倍的dp[i-1][j-1]個數。
如果a[i]和b[j]不相等的話,減去乙個dp[i-1][j-1]個數即可。
本題中另乙個注意點就是dp[i][j]可能為負,此時的處理方法是加上乙個mod
**如下:
1 #include2 #include3 #include4#define mod 1000000007
5#define ll long long
6using
namespace
std;
7 ll dp[1005][1005
];8 ll a[1005
];9 ll b[1005
];10
intmain()
1132
}33 printf("
%i64d\n
",dp[n][m]);34}
35return0;
36 }
多校聯合訓練4 5773
解題方法 0可以轉化成任意整數,包括負數,顯然求lis時盡量把0都放進去必定是正確的。因此我們可以把0拿出來,對剩下的做o nlogn 的lis,統計結果的時候再算上0的數量。為了保證嚴格遞增,我們可以將每個權值s i 減去i前面0的個數,再做lis,就能保證結果是嚴格遞增的。ac include ...
多校聯合訓練10 HDU 5861 Road
題意 給你n個村莊,每兩個相鄰的村莊有一條路,m個操作,每次都要從乙個村莊走到另外乙個村莊,每一條路每次都有乙個維修的費用,每條路一開始是關閉的,你可以開啟一次,關閉一次。問你最少的費用是多少。解題方法 copy一遍題解 為了使得花費最小,對於一段路來說,它的開啟時間就是最早一次被用到到最後一次被用...
2018多校聯合訓練2
打的慘不忍睹,就過了3題 1004 水題,直接輸出yes就過了,solved by lyy include using namespace std define ll long long int n int main return 0 1010 逆序對 min x,y 隊友一開始wa了4發,給了他模...