これは、動的計画法について私が取り組んでいる小さな演習です。私は次の機能を持っています:
この関数を 2 つのアプローチ (メモ化によるトップダウンとボトムアップ) でプログラムする必要があります。
ボトムアップのために私が現在行っていることは次のとおりです。
public static int functionBottomUp (int n){
int [] array = new int[n+1];
array[0] = 1;
for(int i = 1; i < array.length; i++){
if(i == 1)
array[i] = array[i - 1];
else {
for(int p = 0; p < i; p ++)
array[i] += array[p];
}
}
return array[n];
}
そしてメモ化のために:
public static int functionMemoization(int n){
int[] array = new int[n+1];
for(int i = 0; i < n; i++)
array[i] = 0;
return compute(array, n);
}
private static int compute(int[] array, int n){
int ans = 0;
if(array[n] > 0)
return array[n];
if(n == 0 || n == 1)
ans = 1;
else
for(int i = 0; i < n; i++)
ans += compute(array, i);
array[n] = ans;
return array[n];
}
両方の正しい出力が得られますが、両方の複雑さを計算するのに苦労しています。
最初の複雑さは、呼び出しと呼び出しを行うためです(これはf(n)
正式な証明ではないことはわかっていますが、これはアイデアを提供するためのものです)。2^n
f(3)
7
f(0)
f(4)
15
f(0)
しかし今、私は両方の関数の複雑さを計算することに行き詰まっています。
ボトムアップ :
複雑さは O(n) であると言えます ( のため
for(int i = 1; i < array.length; i++)
) が、この内部ループがありfor(int p = 0; p < i; p ++)
、これが複雑さを変更するかどうかはわかりません。
メモ化 :
配列を初期化する最初のループのため、明らかにこれはほとんどの O(n) です。しかし、計算関数がこの複雑さをどのように変更できるかはわかりません。
誰かが私のためにこれを明確にすることができますか?