创建一系列唯一的随机数字

时间:2015-06-17 12:26:51

标签: arrays perl foreach unique

我有以下代码

use strict;
use warnings;
use 5.22.0;

# Generating random seed using 
# Programming Perl p. 955
srand( time() ^ ($$ + ($$ << 15 ) ) );

# Generating code that could have duplicates
my @code = (
    (int(rand(9)) + 1),
    (int(rand(9)) + 1),
    (int(rand(9)) + 1),
    (int(rand(9)) + 1)
);

# Trying to remove duplicates and choosing the unique code
my %seen = ();
my @unique = grep { ! $seen{ $_ }++ } @code;
say @unique;

我正在生成一个包含四个随机数的列表,我需要确保所有四个数字都是唯一的。我能够清除唯一的数字,但并不总是保持标量长度为4。

我最初的想法是进行foreach循环检查以查看每个元素是否相同,但必须有更快的方法来执行此操作。

这是我最初的想法(不使用独特的设置)

my $index = 0
foreach my $element (@code) {
    if ($element == $code[index]) {  
        # repopulate @code at said element
        $code[$index] = (int(rand(9)) + 1);
    }
    $index++;
 }

但是,我认为这可能会给我带来同样的问题,因为可能会有重复。

有没有更快的方法来保持我的阵列中的四个数字都是唯一的?

2 个答案:

答案 0 :(得分:2)

要生成四个唯一非零小数位的列表,请使用List::Util中的shuffle并选择前四位

喜欢这个

use strict;
use warnings;
use 5.010;

use List::Util 'shuffle';

my @unique = (shuffle 1 .. 9)[0..3];

say "@unique";

<强>输出

8 5 1 4

当Perl为你做的时候,没有必要为随机数生成器播种。如果您需要可重复的随机序列

,请仅使用srand

<强>更新

这是另一种类似于你已经拥有的方式。基本上它只是随机编号,直到它有四个不同的

use strict;
use warnings;
use 5.010;

my %unique;
++$unique{int(rand 9) + 1} while keys %unique < 4;

say join ' ', keys %unique;

答案 1 :(得分:0)

@Boromir为您提供了最干净的解决方案。如果你确实需要使用rand(),那么首先要保留副本,而不是在以后删除它们:

#!/usr/bin/perl
use strict;
use warnings;
use 5.22.0;
# Generating random seed using 
# Programming Perl p. 955
srand(time()^($$+($$<<15)));

#Generating code that can't have duplicates
my %seen = ();
while (scalar(keys(%seen)!=4)) {
    $seen{int(rand(9)) + 1}++
}
say keys %seen;