これはDPを実装するのにはかなり有名な例ですが、何らかの理由で私はアルゴリズムを完全に理解することができず、かなり長い間(olympiadを計算するために)執着しています。問題は次のとおりですワインの選択動的プログラミング
棚には、N個のワインが並んでいるとします。わかりやすくするために、左から右へワイン番号をつけましょう。 は、1からNまでの整数、それぞれ で棚に立っています。 i番目のワインの価格はpiです(異なるワインの の価格は異なる場合があります)。
今日は年間とすると、i番目のワインの価格はy * piになります。つまり、今年度の の値のy倍になります。
あなたはすべてのワインを売りたいが、今年からは1年に1本のワインを正確に 販売したいと思う。もう1つの制約 - の場合、一番左のワインまたは 右のワインのみを棚に置いて販売することが許可されており、 ワインを棚に並べ替えることはできません(つまり、最初は )。
あなたは何を最適な順序で
をワインを販売 場合、あなたが得ることができる最大の利益であるとC++での溶液をメモ化と解決策があります(与えられたが、ことをされて、知りたいですほとんど)私の疑問事項ません:
int p[N]; // read-only array of wine prices
// year represents the current year (starts with 1)
// [be, en] represents the interval of the unsold wines on the shelf
int profit(int year, int be, int en) {
// there are no more wines on the shelf
if (be > en)
return 0;
// try to sell the leftmost or the rightmost wine, recursively calculate the
// answer and return the better one
return max(
profit(year+1, be+1, en) + year * p[be],
profit(year+1, be, en-1) + year * p[en]);
}
私が持っている主な混乱は、最大()関数に関連して、我々はこれまで私が理解できるようusing.Asあり、再帰的な利益()関数は、総どうなるか計算し昨年ワイン1を販売した場合の利益と、私たちが去年にワイン2を売ったのならば、それは後の年に売られたワイン1がもっと大きい総利益を持っていると言うことができるので、実際にワイン1を保つべきではありません。 )、ワイン2を売る(それはワイン1よりも利益が少ない)、あるいは私が得られないものがあるか?
"メモがある解決策はありますが、疑いの余地はほとんどありません。"動的プログラミングはある種のメモです。それをスキップすると、それはちょっと不気味な非効率なアルゴリズムに過ぎません。 – Yakk
@ Yakk OPはDP自体に問題はありませんが、この問題の再帰式を取得する方法はあります。したがって、彼のメモは、彼の特定の質問については問題ではないと言ったとき、彼は正しい。 – fjardon