日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

ccpc河北大学生程序设计竞赛dp小总结

發(fā)布時(shí)間:2023/12/13 编程问答 44 豆豆
生活随笔 收集整理的這篇文章主要介紹了 ccpc河北大学生程序设计竞赛dp小总结 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

近期題目來(lái)自校賽,賽前訓(xùn)練,省賽熱身,河北ccpc正式比賽。

題目一:

題目描述:

由于第m個(gè)臺(tái)階上有好吃的薯?xiàng)l,所以薯片現(xiàn)在要爬一段m階的樓梯.
薯片每步最多能爬k個(gè)階梯,但是每到了第i個(gè)臺(tái)階,薯片身上的糖果都會(huì)掉落ai個(gè),現(xiàn)在問(wèn)你薯片至少得掉多少糖果才能得到薯?xiàng)l?

輸入:

多組數(shù)據(jù)輸入,每組數(shù)據(jù)第一行輸入兩個(gè)數(shù)字m(1<m<=1000),k(1<=k<m),接下來(lái)有m行,每一行輸入ai(0<ai<=1000),表示第i個(gè)臺(tái)階會(huì)掉落的糖果.

輸出:

對(duì)于每組數(shù)據(jù),輸出至少要犧牲的糖果數(shù).

樣例輸入

5 2
1 2 3 4 5
6 2
6 5 4 3 2 1

樣例輸出

9
9

分析:經(jīng)過(guò)的數(shù)字全部加起來(lái),為一個(gè)累加和,求最小累加和

遞推關(guān)系:

定義f(n)為必須到第n個(gè)臺(tái)階的最少累加和

分析可以如何得到f(n),我們通過(guò)跳一步,可以怎么跳到第n個(gè)臺(tái)階呢?

可以從第n-1個(gè)臺(tái)階跳到這里,可以n-2,n-3......n-k。

也就是說(shuō),

f(n)=an+min(f(n-1),f(n-2),......f(n-k))

必須到第n個(gè)臺(tái)階的最少累加和,就等于能跳到這里的所有位置中,最小的那個(gè)f(),跳過(guò)來(lái)(也就是加上本身)。

注意:前k個(gè)臺(tái)階可以從起點(diǎn)直接跳過(guò)來(lái),貪心思想,經(jīng)過(guò)任何多余的數(shù)字都不會(huì)是最優(yōu)解。所以前k個(gè)f(n)直接賦值an.

也可以維持單調(diào)隊(duì)列把時(shí)間降到線性,不過(guò)o(n*k)已經(jīng)足夠過(guò)了。

?

題目二:

題目描述:

JiangYu的小金庫(kù)是一個(gè)三維立體的空間,大小為XYZ,里面每個(gè)位置都藏著各種價(jià)值的寶物,既然是寶物價(jià)值自然非同一般,可正可負(fù)。

可惡的花花得知了這一切,想要偷走其中的珍寶們。

可是Jiangyu的小金庫(kù)安保措施十分嚴(yán)密,花花只有一次行動(dòng)的機(jī)會(huì),他決定偷走一個(gè)價(jià)值盡可能大的長(zhǎng)方體區(qū)間。

那么他最大能偷走多少錢的寶物呢?

輸入:

第一行給出三個(gè)正整數(shù) X,Y,Z

第二行一個(gè)整數(shù)n, 寶藏的數(shù)量

接下來(lái)n行,每行給出一個(gè)寶藏的位置xi,yi,zi, 以及價(jià)值ci

保證寶藏位置不重復(fù)。 (1 \leq X,Y,Z \leq 201≤X,Y,Z≤20)

(1 \leq n \leq X \times Y \times Z1≤n≤X×Y×Z)

(1 \leq xi \leq X1≤xi≤X)

(1 \leq yi \leq Y1≤yi≤Y)

(1 \leq zi \leq Z1≤zi≤Z)

(-1e9 \leq ci \leq 1e9?1e9≤ci≤1e9)

輸出:

一個(gè)整數(shù),最大的價(jià)值

樣例輸入

2 2 2
8
1 1 1 10
1 1 2 9
1 2 1 10
1 2 2 9
2 1 1 10
2 1 2 9
2 2 1 -1
2 2 2 10

樣例輸出

66

?

https://blog.csdn.net/hebtu666/article/details/82788866這個(gè)網(wǎng)址寫了詳細(xì)講解哦。。。最好要看看

首先要明白一維最大子數(shù)組問(wèn)題,設(shè)dp[n]的含義為必須以an結(jié)尾的數(shù)組中的最大和。

所以dp[n]就是,每一個(gè)以在n前面的結(jié)尾的最大值,加上an.

二維方法:轉(zhuǎn)化為一維來(lái)做。枚舉長(zhǎng)度為原矩陣長(zhǎng)度的所有矩陣。然后壓成一維來(lái)做。

時(shí)間:

因?yàn)橛衝個(gè)開(kāi)頭,每個(gè)開(kāi)頭有n-1,n-2......1個(gè)結(jié)尾,所以枚舉的時(shí)間復(fù)雜度為o(n^2)。

為了節(jié)省時(shí)間,利用預(yù)處理數(shù)組思想,定義長(zhǎng)寬和原矩陣一樣的矩陣gg。

每列滿足第n列k行的值為sum(l[0][n]+l[1][n]....l[k][n]),可以o(n*m)做到(nm為長(zhǎng)寬).然后枚舉到某矩陣的時(shí)候直接根據(jù)gg得出。整體做到o(n^2)枚舉并求和。然后按一維做。整體o(n^3)

三維:并沒(méi)有什么高大上的優(yōu)化,也是枚舉每一個(gè)長(zhǎng)寬固定的長(zhǎng)方體,壓縮至二維,然后按二維做。

?

題目三:

熱身賽,并沒(méi)有原題,手打。

過(guò)的隊(duì)伍不多

一種動(dòng)物,出生到死亡只有三年,即n年出生,n+3年死去。

出生一年以后可以生育,也就是n+1年開(kāi)始生育,一年可以生一只寶寶。

定義第n年動(dòng)物總數(shù)為an,給定n,返回an/a(n-1),最多保存小數(shù)點(diǎn)后十位

第一年有一只

思路一:定義f(n)為第n年新出生的動(dòng)物個(gè)數(shù),則f(n)=f(n-1)+f(n-2),前兩項(xiàng)為1,而每年的總數(shù)也就是三項(xiàng)求和而已。

每年出生的數(shù)量為1,1,2,3,5,8,13,21

每年總數(shù)就是1,2,4,10,16,26,42

發(fā)現(xiàn)是斐波那契數(shù)列

思路二:直接從總數(shù)入手,定義f(n)為第n年的總數(shù)

如何求出an/a(n-1):要看有多少動(dòng)物能活到n年,活不到n年的也不能在第n年生育,活到n年的動(dòng)物每人生一個(gè),所以an就是二倍的能活到n年的動(dòng)物。求此數(shù)方法很多,在此只說(shuō)一個(gè):

f(n-1)-(1/2)f(n-3)

去年的數(shù)量減去,去年還活著的今年就死了的數(shù)量。

這個(gè)數(shù)乘二,得出答案f(n)=2f(n-1)-f(n-3),其實(shí)本質(zhì)還是斐波那契,因?yàn)閒(n-1)=f(n-2)+f(n-3),帶入以后發(fā)現(xiàn)f(n)=f(n-1)+f(n-2)。

式子寫出來(lái)了,但是原題數(shù)據(jù)范圍是10^1000,不能一項(xiàng)一項(xiàng)推過(guò)去。

嘗試發(fā)現(xiàn),幾十項(xiàng)之后,an/a(n-1)的十位小數(shù)之內(nèi)都沒(méi)有變過(guò),所以當(dāng)數(shù)字較大時(shí)直接輸出第五十項(xiàng)即可。

本題結(jié)束

但是還有點(diǎn)別的東西想寫

?

斐波那契的美

萬(wàn)物之美,總能找到斐波那契數(shù)列的規(guī)律。隨著n的增加,an/a(n-1)越來(lái)越接近黃金分割

手寫了求解過(guò)程??赡軐懙牟灰?guī)范,但是就是表達(dá)這個(gè)意思。

?

只要數(shù)列滿足X(n) = X(n-1) + X(n-2),無(wú)論前兩個(gè)值是多少,都滿足黃金分割的條件,而斐波那契數(shù)列是最簡(jiǎn)單的特例:前兩個(gè)元素均為1

數(shù)學(xué)家還發(fā)現(xiàn)了費(fèi)馬大定理和這個(gè)數(shù)列的關(guān)系(費(fèi)馬大定理的證明,三百五十年),并應(yīng)用到諸多領(lǐng)域(比如加密)。有興趣自行了解。

?

題目四:

省賽,沒(méi)有原題。十六支隊(duì)伍過(guò)了這個(gè)題。

https://blog.csdn.net/hebtu666/article/details/79964233

參考我前面的文章,dp入門篇,那個(gè)會(huì)了這個(gè)就會(huì)。

參考萌新題

現(xiàn)場(chǎng)因?yàn)閷?duì)c++不熟,沒(méi)敢壓空間,規(guī)規(guī)矩矩的寫了一遍,還因?yàn)槎啻蛄艘恍辛P了時(shí),跟智障一樣。。。

?

?

題目五

http://newoj.acmclub.cn/contests/1359/problem/6

題意:最長(zhǎng)公共子序列,要求序列每個(gè)元素重復(fù)k次,比如1122重復(fù)兩次,111222重復(fù)三次。

輸入兩個(gè)字符串和k,輸出長(zhǎng)度。

最長(zhǎng)公共子序列的一個(gè)變形。。。

動(dòng)態(tài)規(guī)劃。設(shè)dp[i][j]表示a串處理到i位置,b串處理到j(luò)位置的答案。預(yù)處理出從a串i位置向前數(shù),第k個(gè)與i位置數(shù)
字相同的位置p[i],用相同方式處理出B串的q[i]。
則轉(zhuǎn)移方程為dp[i][j]=max(dp[i-1][j],dp[i][j-1],dp[i-p[i]][j-q[j]]+1),其中第三種轉(zhuǎn)移必須在a[i]=b[j]的情況下轉(zhuǎn)移。

?

#include <bits/stdc++.h> using namespace std; int k,n,m,dp[1005][1005]; int a[1005],b[1005]; int pa[1005]={0},pb[1005]={0}; queue<int> q[1005]; int main() {int ak; cin>>ak;while(ak--){for(int i=1;i<=n;i++)while(!q[i].empty()) q[i].pop();scanf("%d%d%d",&k,&n,&m);memset(dp,0,sizeof(dp));memset(pa,0,sizeof(pa));memset(pb,0,sizeof(pb));for(int i=1;i<=n;i++) cin>>a[i];for(int i=1;i<=m;i++) cin>>b[i];for(int i=1;i<=n;i++){q[a[i]].push(i);if(q[a[i]].size()==k){pa[i]=q[a[i]].front();q[a[i]].pop();}}for(int i=1;i<=n;i++)while(!q[i].empty()) q[i].pop();for(int i=1;i<=m;i++){q[b[i]].push(i);if(q[b[i]].size()==k){pb[i]=q[b[i]].front();q[b[i]].pop();}}for(int i=1;i<=n;i++){for(int j=1;j<=m;j++){dp[i][j]=max(dp[i-1][j],dp[i][j-1]);if(a[i]==b[j] && pa[i]!=0 && pb[j]!=0)dp[i][j]=dp[pa[i]-1][pb[j]-1]+k;}}printf("%d\n",dp[n][m]);}return 0; }

代碼都是比賽時(shí)候?qū)懙?#xff0c;真的不想找來(lái)貼了。

?

最后總結(jié)經(jīng)驗(yàn)教訓(xùn):

?

注意細(xì)節(jié),注意細(xì)節(jié),注意細(xì)節(jié)

多種思路,多種思路,多種思路

遞歸關(guān)系自己推,比如背包,你要是看套路。。。Emmm。。就連套路都不會(huì)用了。

平時(shí)遞歸關(guān)系自己推,自己推,自己推。

?

總結(jié)

以上是生活随笔為你收集整理的ccpc河北大学生程序设计竞赛dp小总结的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。