Can a seeded shuffle be reversed?

空扰寡人 提交于 2019-12-12 07:19:15

问题


Take this function, which is a seeded Fisher-Yates shuffle (the order is random, but reproducible given the same seed):

function seeded_shuffle(array &$items, $seed = false) {
    $items = array_values($items);
    mt_srand($seed ? $seed : time());
    for ($i = count($items) - 1; $i > 0; $i--) {
        $j = mt_rand(0, $i);
        list($items[$i], $items[$j]) = array($items[$j], $items[$i]);
    }
}

Can this algorithm be reversed? I.e., given the seed value and the shuffled array, can the array be "unshuffled" into its original order? If so, how?

(The question came up in the comments here.)


回答1:


Turns out the answer is yes, and pretty simple:

function seeded_unshuffle(array &$items, $seed) {
    $items = array_values($items);

    mt_srand($seed);
    $indices = [];
    for ($i = count($items) - 1; $i > 0; $i--) {
        $indices[$i] = mt_rand(0, $i);
    }

    foreach (array_reverse($indices, true) as $i => $j) {
        list($items[$i], $items[$j]) = [$items[$j], $items[$i]];
    }
}

Just generate the same random number sequence using the known seed, and traverse it in reverse.



来源:https://stackoverflow.com/questions/24262147/can-a-seeded-shuffle-be-reversed

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!