【问题标题】:Recursive nested loop c#递归嵌套循环c#
【发布时间】:2014-09-14 09:56:59
【问题描述】:

我正在尝试通过一项任务提高自己的概率,但无法弄清楚: 在西洋双陆棋游戏中,我有四行(动态)展示位置。

假设第 5、7、11、13 行。我正在扔动态数量的骰子。我试图找到每个游戏的概率。举个例子:

我掷了 4 个骰子,结果是 1,3,4,6

所以

我可以玩 5. row-1,3,4,6 骰子

我可以从 5. row-1,3,4 骰子和 7. row-6 骰子玩

我可以从 5. row-3,1 骰子、11. row-6 骰子和 13. row-4 骰子开始游戏 等等等等。

骰子必须是动态的,行必须是动态的,骰子可以像 1,3,4,6 或 6,1,4,3 或 3,1,6,4 一样混合播放。并且它必须计算在行上散布的骰子的不同变化的所有可能性。

我只是想计算玩无限骰子的西洋双陆棋的可能性。我试图用它来拥有一个可调整大小的可能移动类的方法,在这个类内部,有可调整大小的行类。在 rows 类中,有一个可调整大小的 List 移动变量。我为每个变化添加一个动作。这是非动态 4 骰子的代码。

public   List<int> dice;
public   List<int> places;

[System.Serializable]
public class arrayData
{
    public List<arrayData2> places = new List<arrayData2>();
    }

    public List<arrayData> pos = new List<arrayData>();

    [System.Serializable]
    public class arrayData2
    {
        public List<int> moves = new List<int> {};
    }

    void Start()
    {
        vs();
    }

    void vs()
    {
        for (int i = 0; i < places.Count; i++)
        {
            for (int a = 0; a < dice.Count; a++)
            {
                for (int b = 0; b < dice.Count; b++)
                {
                    for (int c = 0; c < dice.Count; c++)
                    {
                        for (int d = 0; d < dice.Count; d++)
                        {
                            if (a == b || a == c || a == d || b == c || b == d || c == d)
                            {
                                continue;
                            }

                            pos.Add(new arrayData());

                            for (int s = 0; s < places.Count; s++)
                            {
                                pos[pos.Count - 1].places.Add(new arrayData2());
                            }

                            pos[pos.Count - 1].places[i].moves.Add(dice[a]);
                            pos[pos.Count - 1].places[i].moves.Add(dice[b]);
                            pos[pos.Count - 1].places[i].moves.Add(dice[c]);
                            pos[pos.Count - 1].places[i].moves.Add(dice[d]);
                        }
                    }
                }
            }
        }
    }

我想不通的:

-首先,我尝试使其成为递归循环,但我无法弄清楚结构

-其次,输出为我提供了行之间分布变化的缺失值:它给出了这样的值:5. row-1,3,4,6 骰子,但没有这样的值:5. row-3,1骰子和第 11 行第 6 行骰子和第 13 行第 4 行骰子

我知道这是一个很大的问题,但任何指出错误或正确方向的人都会非常感激。

谢谢

【问题讨论】:

标签: c# loops recursion nested permutation


【解决方案1】:

将您的动作考虑为game tree 的一部分可能会很有用。基本思想是所有游戏都以特定状态开始。我们称之为x。然后移动将游戏状态更改为x1,下一个移动更改为x2,依此类推。大多数动作都涉及一个选择,并且根据所做的选择,每个动作都会将游戏推入不同的状态。从初始状态开始,所有可能的移动形成一棵巨大的树。这很方便,因为我们可以使用tree traversal algorithms 来探索我们的树。这就是递归的用武之地。

西洋双陆棋在概念上比国际象棋或跳棋等游戏要复杂一些,因为您必须考虑骰子的随机性以及对手的行为。这在移动过程中增加了更多选择。在伪代码中,我可能会这样解决问题:

function get_next_move (current_state):
    dice = roll_dice()
    possible_states = an empty collection
    get_possible_states (dice, current_state, possible_states)
    return decide_best_state (possible_states)

function get_possible_states (dice, state, possible_states):

    // If we've exhausted all dice, we're done.
    // Add the state we've reached to our possible outcomes.
    if dice are empty:
        add state to possible_states
        return            

    for each die in dice:
        dice_without_die = remove die from dice
        for each next_state in get_legal_states (state, die):
            // Here's the recursion. Go a level deeper in our tree.
            get_possible_states (dice_without_die , next_state, possible_states)


function get_legal_states (state, die):
    // Here's where you determine legal moves based on the
    // die rolled and the current state of the game.

换句话说,要确定我的下一步行动,我必须:

  1. 掷骰子。
  2. 每掷一次骰子,生成其所有合法移动(状态)。
  3. 使用新状态重复该过程,而无需使用已使用的模具。
  4. 当没有骰子剩下时,将最终状态添加到可能状态列表中。
  5. 最后,确定哪个动作最好。请记住,某些生成的状态可能是重复的。将您的作品移至相同位置的方法不止一种。

这种方法的好处是没有硬编码的数字。它可以处理任意数量的合法移动或骰子。 (虽然我不确定步步高何时会使用可变数量的骰子。)我遗漏的一个细节是你需要知道轮到谁了。法律行动将取决于制造者。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-05-19
    • 1970-01-01
    • 1970-01-01
    • 2018-11-11
    • 2010-12-12
    • 1970-01-01
    相关资源
    最近更新 更多