【问题标题】:PHP endless loop, why?PHP无限循环,为什么?
【发布时间】:2017-09-29 06:12:14
【问题描述】:

这是我的代码。我不明白为什么我会陷入无限循环。 我认为当我为数组创建唯一的随机值时,$check 必须停止循环。

    <?php

        $foo["blue"] = 0;
        $foo["black"] = 0;
        $foo["red"] = 0;
        $foo["white"] = 0;

        $check;
        do
        {
            foreach($foo as &$val)
            {
                $val = rand(1,6);
            }

            $foo = array_unique($foo);
            $check = count($foo);

        }
        while($check != 4);

        echo '............................ <br>';
        foreach($foo as $key=>$value)
        {
            echo $key . ' ' . $value . '<br>';
        }

    ?>

【问题讨论】:

  • 尝试将print_r($foo); 放入do-while 循环以查看值是什么。
  • @ishegg 没关系,这就是在foreach 循环中更新当前数组元素的方式。
  • $foo = array_unique($foo)。如果在第一次迭代之后,数组有重复值,那么该行将使$foo 成为一个包含三个或更少元素的数组,因此$check 将始终不同于 4,因此循环将是无限的。循环停止的唯一方法是在第一次迭代后获得四个不同的随机值。

标签: php loops


【解决方案1】:

问题是第一次通过循环有一些重复,所以array_unique() 将数组从 4 个元素减少到 1、2 或 3。foreach 循环永远无法使数组再次变大,因为它只循环数组中当前存在的元素。所以一旦数组缩小,它就永远不会增长回 4 个元素,$check != 4 将永远为真。

你应该得到数组的原始键并使用它。

<?php

    $foo["blue"] = 0;
    $foo["black"] = 0;
    $foo["red"] = 0;
    $foo["white"] = 0;
    $keys = array_keys($foo);

    $check;
    do
    {
        foreach($keys as $i)
        {
            $foo[$i] = rand(1,6);
        }

        $foo = array_unique($foo);
        $check = count($foo);

    }
    while($check != 4);

    echo '............................ <br>';
    foreach($foo as $key=>$value)
    {
        echo $key . ' ' . $value . '<br>';
    }

?>

DEMO

【讨论】:

    【解决方案2】:

    就我个人而言,我不会在熵如此低的循环中这样做,因为最终匹配一个随机集可能需要一整天的时间。

    更好的方法是生成一个范围并将其随机化,然后遍历您的数组并设置值。

    <?php
    $rand = range(1, 6);
    shuffle($rand);
    
    $foo["blue"] = 0;
    $foo["black"] = 0;
    $foo["red"] = 0;
    $foo["white"] = 0;
    
    $i=0;
    foreach ($foo as $key => $value) {
        $foo[$key] = $rand[$i];
        $i++;
    }
    
    print_r($foo);
    /*Array
    (
        [blue] => 1
        [black] => 3
        [red] => 2
        [white] => 5
    )
    */
    

    https://3v4l.org/4hPku

    【讨论】:

    • 谢谢。我现在明白了。
    猜你喜欢
    • 1970-01-01
    • 2012-11-12
    • 2010-10-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-08-08
    • 2020-02-20
    • 2012-11-06
    相关资源
    最近更新 更多