0

このアルゴリズム(ProjectEulerの問題15を解決するために使用した)の機能を非再帰的な方法で書き直したいと思います。

はい、実際の問題を解決するためのより良い方法はたくさんあると思いますが、課題として、このロジックを可能な限り単純化したいと思います。

public class SolveRecursion
{
    public long Combination = 0;
    public int GridSize;

    public void CalculateCombination(int x = 0, int y = 0)
    {
        if (x < GridSize)
        {
            CalculateCombination(x + 1, y);
        }
        if (y < GridSize)
        {
            CalculateCombination(x, y + 1);
        }
        if (x == GridSize && y == GridSize)
            Combination++;
    }
}

そしてテスト:

[Test]
public void SolveRecursion_GivenThree_GivesAnswerOf20Routes()
{
    solveRecursion.GridSize = 3;
    solveRecursion.CalculateCombination();
    var result = solveRecursion.Combination;
    Assert.AreEqual(20, result);
}

[Test]
public void SolveRecursion_GivenFour_GivesAnswerOf70Routes()
{
    solveRecursion.GridSize = 4;
    solveRecursion.CalculateCombination();
    var result = solveRecursion.Combination;
    Assert.AreEqual(70, result);
}

編集:これは両方の方法で書かれた別の単純な関数です:

//recursion
private int Factorial(int number)
{
    if (number == 0)
        return 1;
    int returnedValue = Factorial(number - 1);

    int result = number*returnedValue;
    return result;
}

//loop
private int FactorialAsLoop(int number)
{
    //4*3*2*1
    for (int i = number-1; i >= 1; i--)
    {
        number = number*i;
    }
    return number;
}

ヒントをいただければ幸いです。私は動的計画法の解決策(より数学に基づいたアプローチを使用する)と、パズルをうまく解くための方程式を試しました。

この最初のアルゴリズムを単純に非再帰的にすることはできますか?

4

1 に答える 1

0

非再帰的なソリューションは次のとおりです。

const int n = 4;
int a[n + 2][n + 2] = {0};

a[0][0] = 1;
for (int i = 0; i < n + 1; ++i)
    for (int j = 0; j < n + 1; ++j) {
        a[i][j + 1] += a[i][j];
        a[i + 1][j] += a[i][j];
    }

std::cout << a[n][n] << std::endl;

参考までに、この問題は紙の上で解決されているはずです。NxMグリッドの答えはC(N + M、N)です。ここで、Cは組み合わせ関数です-http://en.wikipedia.org/wiki/Combination

于 2013-08-26T17:20:46.940 に答える