在php中生成加密安全的随机数

时间:2022-11-25 19:42:52

PHP's rand() function doesn't give good random numbers. So I started to use mt_rand() which is said to give better results. But how good are these results? Are there any methods to improve them again?

PHP的rand()函数没有给出好的随机数。所以我开始使用mt_rand(),据说可以提供更好的结果。但这些结果有多好?有没有什么方法可以再次改善它们?

My idea:

我的想法:

function rand_best($min, $max) {
    $generated = array();
    for ($i = 0; $i < 100; $i++) {
        $generated[] = mt_rand($min, $max);
    }
    shuffle($generated);
    $position = mt_rand(0, 99);
    return $generated[$position];
}

This should give you "perfect" random numbers, shouldn't it?

这应该给你“完美”的随机数,不应该吗?

16 个解决方案

#1


32  

Pseudorandom number generators (PRNG) are very complex beast.

伪随机数发生器(PRNG)是非常复杂的野兽。

There are no real "perfect" random number generators -- in fact the best that can be done from mathematical functions are pseudorandom -- they seem random enough for most intents and purposes.

没有真正的“完美”随机数生成器 - 事实上,从数学函数中可以做到的最好的是伪随机 - 它们对于大多数意图和目的来说似乎是随机的。

In fact, performing any additional actions from a number returned by a PRNG doesn't really increase its randomness, and in fact, the number can become less random.

实际上,从PRNG返回的数字执行任何其他操作并不会真正增加其随机性,事实上,该数字可能变得不那么随机。

So, my best advice is, don't mess around with values returned from a PRNG. Use a PRNG that is good enough for the intended use, and if it isn't, then find a PRNG that can produce better results, if necessary.

所以,我最好的建议是,不要搞乱从PRNG返回的值。使用对于预期用途而言足够好的PRNG,如果不是,则找到可以产生更好结果的PRNG,如果必要的话。

And frankly, it appears that the mt_rand function uses the Mersenne twister, which is a pretty good PRNG as it is, so it's probably going to be good enough for most casual use.

坦率地说,似乎mt_rand函数使用了Mersenne twister,这是一个相当不错的PRNG,因此对于大多数休闲用途来说它可能已经足够好了。

However, Mersenne Twister is not designed to be used in any security contexts. See this answer for a solution to use when you need randomness to ensure security.

但是,Mersenne Twister并非设计用于任何安全环境。有关在需要随机性以确保安全性时使用的解决方案,请参阅此答案。

Edit

编辑

There was a question in the comments why performing operations on a random number can make it less random. For example, some PRNGs can return more consistent, less random numbers in different parts of the bits -- the high-end can be more random than the low-end.

评论中有一个问题,为什么对随机数执行操作可以减少随机数。例如,一些PRNG可以在比特的不同部分返回更一致,更少随机的数字 - 高端可以比低端更随机。

Therefore, in operations where the high-end is discarded, and the low end is returned, the value can become less random than the original value returned from the PRNG.

因此,在丢弃高端并且返回低端的操作中,该值可以变得比从PRNG返回的原始值更不随机。

I can't find a good explanation at the moment, but I based that from the Java documentation for the Random.nextInt(int) method, which is designed to create a fairly random value in a specified range. That method takes into account the difference in randomness of the parts of the value, so it can return a better random number compared to more naive implementations such as rand() % range.

我目前找不到一个好的解释,但是我基于Random.nextInt(int)方法的Java文档,它是为了在指定范围内创建一个相当随机的值。该方法考虑了值的各部分的随机性差异,因此与更天真的实现(例如rand()%range)相比,它可以返回更好的随机数。

#2


22  

Quick answer:

快速回答:

In a new PHP7 there is a finally a support for a cryptographically secure pseudo-random integers.

在新的PHP7中,最终支持加密安全的伪随机整数。

int random_int ( int $min , int $max )

There is also a polyfill for PHP5x.

PHP5x还有一个polyfill。

Longer answer

更长的答案


There is no perfect random number generator, and computers use pseudorandom number generator to create sequences that looks random. The sequences look random (and pass some randomness tests) but because there is some algorithm to generate it, you can repeat algorithm with absolutely the same states and get the same result.

没有完美的随机数生成器,计算机使用伪随机数生成器来创建看起来随机的序列。序列看起来是随机的(并通过一些随机性测试),但因为有一些算法来生成它,你可以用完全相同的状态重复算法并得到相同的结果。

The same advice as with cryptography "do not invent your own cypher" can be translated to random number generators and mean that you can not just get a lot of random number generators combined together and get expect to get a better generator.

与加密“不发明自己的密码”相同的建议可以转换为随机数生成器,这意味着你不能只是将大量随机数生成器组合在一起并期望得到更好的生成器。


One of the subsets of random number generators is cryptographically secure random number generators:

随机数生成器的子集之一是加密安全随机数生成器:

The requirements of an ordinary PRNG are also satisfied by a cryptographically secure PRNG, but the reverse is not true. CSPRNG requirements fall into two groups: first, that they pass statistical randomness tests; and secondly, that they hold up well under serious attack, even when part of their initial or running state becomes available to an attacker

普通PRNG的要求也由加密安全的PRNG满足,但反之则不然。 CSPRNG要求分为两组:第一,他们通过统计随机性测试;第二,他们在严重攻击下保持良好状态,即使他们的初始或运行状态的一部分可供攻击者使用

So this is pretty close to your definition of "perfect". One more time under no condition (except of learning how to do cryptography) you should try to implement one of that algorithms and use it in your system.

所以这非常接近你对“完美”的定义。在没有条件的情况下再次(除了学习如何进行加密)之外,您应该尝试实现其中一种算法并在系统中使用它。


But luckily PHP7 has it implemented,

但幸运的是PHP7实现了它,

int random_int ( int $min , int $max )

Generates cryptographic random integers that are suitable for use where unbiased results are critical (i.e. shuffling a Poker deck).

生成适用于无偏结果至关重要的加密随机整数(即改组扑克牌组)。

The sources of random are as follows:

随机来源如下:

  • On Windows CryptGenRandom() is used exclusively
  • 在Windows上CryptGenRandom()是专门使用的
  • arc4random_buf() is used if it is available (generally BSD specific)
  • 如果可用,则使用arc4random_buf()(通常是BSD特定的)
  • /dev/arandom is used where available
  • / dev / arandom用于可用的地方
  • The getrandom(2) syscall (on newer Linux kernels)
  • getrandom(2)系统调用(在较新的Linux内核上)
  • /dev/urandom is used where none of the above is available
  • / dev / urandom用于以上都不可用的地方

This makes all the previous answers obsolete (and some deprecated).

这使得之前的所有答案都已过时(有些已弃用)。

#3


17  

I'm not sure that what you've done "improves" the randomness. From what I can understand you generate 100 random numbers and then randomly pick one of them.

我不确定你所做的“改善”随机性。根据我的理解,您生成100个随机数,然后随机选择其中一个。

From what I can remember from my probability course, this probably doesn't increase the randomness, as if there is an underlying bias in the generator function (mt_rand()), then it will still be reflected somehow in the output.

从我记忆中的概率过程来看,这可能不会增加随机性,就好像生成器函数中存在潜在的偏差(mt_rand()),然后它仍然会以某种方式反映在输出中。

#4


13  

In what way is mt_rand() "bad"?

mt_rand()以什么方式“坏”?

For example: If it favors a certain number. Lets say mt_rand(1, 10) favours low numbers in the range, ie "1" and "2" occurs on average more than 10% each. Then your "improvement" would still suffer from the same problem.

例如:如果它有利于某个数字。让我们说mt_rand(1,10)有利于该范围内的低数字,即“1”和“2”平均每个超过10%。那么你的“改进”仍然会遇到同样的问题。

Selecting a random number out of a faulty sequence will still be faulty.

从故障序列中选择随机数仍然有问题。

#5


12  

<?php
  function random_number(){
      return 4; // return generated number
                // guaranteed to be random
  }
  ?>

All joking aside, you're getting into a philosophical question of what is "random" or what is "best". Ideally you'd want your random numbers to have few patterns in them over the course of your procedure. Generally system time is used as the seed, but I've also used the previous random number as the seed, the previous random numberth ago as the seed. The problem is, with a powerful enough computer and full knowledge of the hardware running, and generator function, you would be able to predict the entire set of numbers generated. Thus if you had a powerful enough computer (some people put God into this category) that knew all possible variables and functions of the universe you would then be able to predict every event that happened or will happen. Most random number generators are fine on their own but if you know someone who can see the patterns, more likely they are like the guy in Beautiful Mind and you should get them checked into a clinic.

除了开玩笑之外,你会陷入一个关于什么是“随机”或什么是“最佳”的哲学问题。理想情况下,您希望随机数在整个过程中几乎没有模式。通常系统时间用作种子,但我也使用先前的随机数作为种子,之前的随机数字作为种子。问题是,凭借足够强大的计算机以及对硬件运行和生成器功能的全面了解,您将能够预测生成的整个数字集。因此,如果你有足够强大的计算机(有些人将上帝置于这个类别中)知道宇宙的所有可能的变量和功能,那么你就能够预测发生或将要发生的每一个事件。大多数随机数生成器本身都很好但如果你知道有人可以看到这些模式,那么他们更像是美丽心灵中的那个人,你应该让他们进入诊所。

By popular demand :D

受欢迎的需求:D

#6


5  

I wrote a cronjob that gets 1000 numbers from random.org periodically (say, once an hour) and added them into a PHP array. Whenever I want random numbers in my script, I use mt_rand(0,1000) to call a number from that. A few extra microseconds of overhead, but I get truly random numbers based on natural atmospheric noise.

我写了一个cronjob,定期从random.org获取1000个数字(比如每小时一次)并将它们添加到PHP数组中。每当我想在我的脚本中使用随机数时,我就使用mt_rand(0,1000)从中调用一个数字。几微秒的开销,但我得到了基于自然大气噪声的真正随机数。

#7


2  

It all depends what for you need that random number :) For me ShuffleBag is the best one :)

这一切都取决于你需要什么随机数:)对我来说ShuffleBag是最好的:)

#8


2  

Edit: My comment is no longer valid. Please see the following answer: https://*.com/a/31443898/109561

编辑:我的评论不再有效。请参阅以下答案:https://*.com/a/31443898/109561


I'm guessing you're worried about the distribution of mt_rand(). I have tested it and it is very level and both bounds are inclusive.

我猜你担心mt_rand()的分布。我测试了它,它非常水平,两个边界都是包容性的。

I added my test to the comments of the documentation for mt_rand() on the php manual, but it was removed by a silly moderator due to politics that are too long winded to go into here.

我在php手册中将我的测试添加到了mt_rand()文档的注释中,但由于政治太长,无法进入此处,因此被一位愚蠢的主持人删除了。

#9


1  

If you don't like PHP's built in rand(), you probably shouldn't use their built-in shuffle() either, since it seems to be built on their rand().

如果你不喜欢PHP的内置rand(),你可能也不应该使用他们的内置shuffle(),因为它似乎是在他们的rand()上构建的。

I am halfway sure the "industry standard" shuffle now is the Fisher-Yates shuffle.

我有一半确定现在的“行业标准”洗牌是费雪耶茨洗牌。

#10


1  

There is no such thing as a "perfect" random number. No matter what subjective definition of "perfect" you have. You can only achieve pseudo-random.

没有“完美”的随机数这样的东西。无论你有什么主观的“完美”定义。你只能实现伪随机。

I was simply trying to point you in the right direction. You asked a question about perfect random numbers, even if perfect was in quotes. And yes, you can improve randomness. You can even implement heuristic or "natural" algorithms, such ideas like "atmospheric noise" -- but still, you're not perfect, not by any means.

我只是想指出你正确的方向。你问了一个关于完美随机数的问题,即使是完美的引号。是的,你可以改善随机性。你甚至可以实现启发式或“自然”算法,比如“大气噪声”这样的想法 - 但是,你并不是完美的,不是任何方式。

#11


1  

use /dev/ramdom (linux device true random number generator) to seed mt_rand

使用/ dev / ramdom(linux device true random number generator)来播种mt_rand

<?
$rnd_dev=mcrypt_create_iv(4, MCRYPT_DEV_RANDOM); //need "apt-get install php5-mcrypt"
$seed=ord(substr($rnd_dev, 0, 1))<<24 |
      ord(substr($rnd_dev, 1, 1))<<16 |
      ord(substr($rnd_dev, 2, 1))<<8 |
      ord(substr($rnd_dev, 3, 1));
mt_srand($seed);
echo mt_rand();
?>

#12


0  

I made a PHP class for generating random numbers and strings PHPRandomValue

我创建了一个PHP类来生成随机数和字符串PHPRandomValue

It uses "mcrypt_create_iv(4, MCRYPT_DEV_URANDOM)" to generate random numbers and values. I made it while working on a crypto project because I needed a safe random value generator. Here's an example usage

它使用“mcrypt_create_iv(4,MCRYPT_DEV_URANDOM)”来生成随机数和值。我在加密项目时做了这个,因为我需要一个安全的随机值生成器。这是一个示例用法

$randomValue = new RandomValue;

$randomValue->randomNumber(): = -3880998

$randomValue->randomNumberBetween(1,10): = 2

$randomValue->randomTextString(): = CfCkKDHRgUULdGWcSqP4

$randomValue->randomTextString(10):  = LorPIxaeEY

$randomValue->randomKey(): = C7al8tX9.gqYLf2ImVt/!$NOY79T5sNCT/6Q.$!.6Gf/Q5zpa3

$randomValue->randomKey(10):  = RDV.dc6Ai/

#13


-1  

It is not possible to generate true random numbers, the best you can hope for is pseudo-random which is what rand() provides, your function is no closer to random then rand(). Take a look at this http://en.wikipedia.org/wiki/Random_number_generator

不可能生成真正的随机数,你可以期望的最好是伪随机,这是rand()提供的,你的函数不再接近随机然后rand()。看看这个http://en.wikipedia.org/wiki/Random_number_generator

#14


-1  

Tru Random numbers

Tru随机数

<?php
for ($i = -1; $i <= 4; $i++) {
    $bytes = openssl_random_pseudo_bytes($i, $cstrong);
    $hex   = bin2hex($bytes);

    echo "Lengths: Bytes: $i and Hex: " . strlen($hex) . PHP_EOL;
    var_dump($hex);
    var_dump($cstrong);
    echo PHP_EOL;
}
?>

and also crypto secure ;)

并且加密安全;)

#15


-2  

Although the answer was accepted years ago, I'll re-reopen it.

虽然答案在几年前就被接受了,但我会重新打开它。

Since all this randomness depends on the system time, let's mess with the system time too! The amount of time an operation takes on the computer is actually rather variable (especially if other stuff is happening on that server), so if we take advantage of that with microtime... (couldn't find any portable nanotime commands)

由于所有这些随机性取决于系统时间,让我们也搞乱系统时间!操作在计算机上花费的时间实际上是相当可变的(特别是如果在该服务器上发生其他事情),所以如果我们利用microtime的那个...(找不到任何便携式纳米级命令)

$a='';
for (int $i=0; $i<9001; $i++)
{
    usleep(mt_rand(1000,10000));//Also eliminates timing attacks... possibly?
    $a=hash('SHA512',$a.uniqid(mt_rand().microtime(),true));
}
echo $a;

Nominally this has 207023 bits of entropy, since you're adding another 23 bits every iteration, but there's a lot of interdependencies, so it's probably a few orders of magnitude less. Still pretty good.

名义上它有207023位的熵,因为你每次迭代都会增加23位,但是它有很多相互依赖性,所以它可能要少几个数量级。还不错。

Do you know of any operations on PHP that take a really random amount of time? Like... HTTP-requesting some website (other than RANDOM.org) and measuring the time it takes?

你知道PHP上的任何操作需要花费很多时间吗?就像...... HTTP请求一些网站(RANDOM.org除外)并测量所需的时间?

#16


-4  

Using random.org, you can use this:

使用random.org,您可以使用:

function getToken($length, $min, $max){
    $r = explode('
',file_get_contents('http://www.random.org/integers/num='.$length.'&min='.$min.'&max='.$max.'&col=1&base=10&format=plain'));

    $string = '';
    foreach ( $r as $char ) $string.=$char;
    return $string;
}

this should give real random numbers

这应该给出真正的随机数

#1


32  

Pseudorandom number generators (PRNG) are very complex beast.

伪随机数发生器(PRNG)是非常复杂的野兽。

There are no real "perfect" random number generators -- in fact the best that can be done from mathematical functions are pseudorandom -- they seem random enough for most intents and purposes.

没有真正的“完美”随机数生成器 - 事实上,从数学函数中可以做到的最好的是伪随机 - 它们对于大多数意图和目的来说似乎是随机的。

In fact, performing any additional actions from a number returned by a PRNG doesn't really increase its randomness, and in fact, the number can become less random.

实际上,从PRNG返回的数字执行任何其他操作并不会真正增加其随机性,事实上,该数字可能变得不那么随机。

So, my best advice is, don't mess around with values returned from a PRNG. Use a PRNG that is good enough for the intended use, and if it isn't, then find a PRNG that can produce better results, if necessary.

所以,我最好的建议是,不要搞乱从PRNG返回的值。使用对于预期用途而言足够好的PRNG,如果不是,则找到可以产生更好结果的PRNG,如果必要的话。

And frankly, it appears that the mt_rand function uses the Mersenne twister, which is a pretty good PRNG as it is, so it's probably going to be good enough for most casual use.

坦率地说,似乎mt_rand函数使用了Mersenne twister,这是一个相当不错的PRNG,因此对于大多数休闲用途来说它可能已经足够好了。

However, Mersenne Twister is not designed to be used in any security contexts. See this answer for a solution to use when you need randomness to ensure security.

但是,Mersenne Twister并非设计用于任何安全环境。有关在需要随机性以确保安全性时使用的解决方案,请参阅此答案。

Edit

编辑

There was a question in the comments why performing operations on a random number can make it less random. For example, some PRNGs can return more consistent, less random numbers in different parts of the bits -- the high-end can be more random than the low-end.

评论中有一个问题,为什么对随机数执行操作可以减少随机数。例如,一些PRNG可以在比特的不同部分返回更一致,更少随机的数字 - 高端可以比低端更随机。

Therefore, in operations where the high-end is discarded, and the low end is returned, the value can become less random than the original value returned from the PRNG.

因此,在丢弃高端并且返回低端的操作中,该值可以变得比从PRNG返回的原始值更不随机。

I can't find a good explanation at the moment, but I based that from the Java documentation for the Random.nextInt(int) method, which is designed to create a fairly random value in a specified range. That method takes into account the difference in randomness of the parts of the value, so it can return a better random number compared to more naive implementations such as rand() % range.

我目前找不到一个好的解释,但是我基于Random.nextInt(int)方法的Java文档,它是为了在指定范围内创建一个相当随机的值。该方法考虑了值的各部分的随机性差异,因此与更天真的实现(例如rand()%range)相比,它可以返回更好的随机数。

#2


22  

Quick answer:

快速回答:

In a new PHP7 there is a finally a support for a cryptographically secure pseudo-random integers.

在新的PHP7中,最终支持加密安全的伪随机整数。

int random_int ( int $min , int $max )

There is also a polyfill for PHP5x.

PHP5x还有一个polyfill。

Longer answer

更长的答案


There is no perfect random number generator, and computers use pseudorandom number generator to create sequences that looks random. The sequences look random (and pass some randomness tests) but because there is some algorithm to generate it, you can repeat algorithm with absolutely the same states and get the same result.

没有完美的随机数生成器,计算机使用伪随机数生成器来创建看起来随机的序列。序列看起来是随机的(并通过一些随机性测试),但因为有一些算法来生成它,你可以用完全相同的状态重复算法并得到相同的结果。

The same advice as with cryptography "do not invent your own cypher" can be translated to random number generators and mean that you can not just get a lot of random number generators combined together and get expect to get a better generator.

与加密“不发明自己的密码”相同的建议可以转换为随机数生成器,这意味着你不能只是将大量随机数生成器组合在一起并期望得到更好的生成器。


One of the subsets of random number generators is cryptographically secure random number generators:

随机数生成器的子集之一是加密安全随机数生成器:

The requirements of an ordinary PRNG are also satisfied by a cryptographically secure PRNG, but the reverse is not true. CSPRNG requirements fall into two groups: first, that they pass statistical randomness tests; and secondly, that they hold up well under serious attack, even when part of their initial or running state becomes available to an attacker

普通PRNG的要求也由加密安全的PRNG满足,但反之则不然。 CSPRNG要求分为两组:第一,他们通过统计随机性测试;第二,他们在严重攻击下保持良好状态,即使他们的初始或运行状态的一部分可供攻击者使用

So this is pretty close to your definition of "perfect". One more time under no condition (except of learning how to do cryptography) you should try to implement one of that algorithms and use it in your system.

所以这非常接近你对“完美”的定义。在没有条件的情况下再次(除了学习如何进行加密)之外,您应该尝试实现其中一种算法并在系统中使用它。


But luckily PHP7 has it implemented,

但幸运的是PHP7实现了它,

int random_int ( int $min , int $max )

Generates cryptographic random integers that are suitable for use where unbiased results are critical (i.e. shuffling a Poker deck).

生成适用于无偏结果至关重要的加密随机整数(即改组扑克牌组)。

The sources of random are as follows:

随机来源如下:

  • On Windows CryptGenRandom() is used exclusively
  • 在Windows上CryptGenRandom()是专门使用的
  • arc4random_buf() is used if it is available (generally BSD specific)
  • 如果可用,则使用arc4random_buf()(通常是BSD特定的)
  • /dev/arandom is used where available
  • / dev / arandom用于可用的地方
  • The getrandom(2) syscall (on newer Linux kernels)
  • getrandom(2)系统调用(在较新的Linux内核上)
  • /dev/urandom is used where none of the above is available
  • / dev / urandom用于以上都不可用的地方

This makes all the previous answers obsolete (and some deprecated).

这使得之前的所有答案都已过时(有些已弃用)。

#3


17  

I'm not sure that what you've done "improves" the randomness. From what I can understand you generate 100 random numbers and then randomly pick one of them.

我不确定你所做的“改善”随机性。根据我的理解,您生成100个随机数,然后随机选择其中一个。

From what I can remember from my probability course, this probably doesn't increase the randomness, as if there is an underlying bias in the generator function (mt_rand()), then it will still be reflected somehow in the output.

从我记忆中的概率过程来看,这可能不会增加随机性,就好像生成器函数中存在潜在的偏差(mt_rand()),然后它仍然会以某种方式反映在输出中。

#4


13  

In what way is mt_rand() "bad"?

mt_rand()以什么方式“坏”?

For example: If it favors a certain number. Lets say mt_rand(1, 10) favours low numbers in the range, ie "1" and "2" occurs on average more than 10% each. Then your "improvement" would still suffer from the same problem.

例如:如果它有利于某个数字。让我们说mt_rand(1,10)有利于该范围内的低数字,即“1”和“2”平均每个超过10%。那么你的“改进”仍然会遇到同样的问题。

Selecting a random number out of a faulty sequence will still be faulty.

从故障序列中选择随机数仍然有问题。

#5


12  

<?php
  function random_number(){
      return 4; // return generated number
                // guaranteed to be random
  }
  ?>

All joking aside, you're getting into a philosophical question of what is "random" or what is "best". Ideally you'd want your random numbers to have few patterns in them over the course of your procedure. Generally system time is used as the seed, but I've also used the previous random number as the seed, the previous random numberth ago as the seed. The problem is, with a powerful enough computer and full knowledge of the hardware running, and generator function, you would be able to predict the entire set of numbers generated. Thus if you had a powerful enough computer (some people put God into this category) that knew all possible variables and functions of the universe you would then be able to predict every event that happened or will happen. Most random number generators are fine on their own but if you know someone who can see the patterns, more likely they are like the guy in Beautiful Mind and you should get them checked into a clinic.

除了开玩笑之外,你会陷入一个关于什么是“随机”或什么是“最佳”的哲学问题。理想情况下,您希望随机数在整个过程中几乎没有模式。通常系统时间用作种子,但我也使用先前的随机数作为种子,之前的随机数字作为种子。问题是,凭借足够强大的计算机以及对硬件运行和生成器功能的全面了解,您将能够预测生成的整个数字集。因此,如果你有足够强大的计算机(有些人将上帝置于这个类别中)知道宇宙的所有可能的变量和功能,那么你就能够预测发生或将要发生的每一个事件。大多数随机数生成器本身都很好但如果你知道有人可以看到这些模式,那么他们更像是美丽心灵中的那个人,你应该让他们进入诊所。

By popular demand :D

受欢迎的需求:D

#6


5  

I wrote a cronjob that gets 1000 numbers from random.org periodically (say, once an hour) and added them into a PHP array. Whenever I want random numbers in my script, I use mt_rand(0,1000) to call a number from that. A few extra microseconds of overhead, but I get truly random numbers based on natural atmospheric noise.

我写了一个cronjob,定期从random.org获取1000个数字(比如每小时一次)并将它们添加到PHP数组中。每当我想在我的脚本中使用随机数时,我就使用mt_rand(0,1000)从中调用一个数字。几微秒的开销,但我得到了基于自然大气噪声的真正随机数。

#7


2  

It all depends what for you need that random number :) For me ShuffleBag is the best one :)

这一切都取决于你需要什么随机数:)对我来说ShuffleBag是最好的:)

#8


2  

Edit: My comment is no longer valid. Please see the following answer: https://*.com/a/31443898/109561

编辑:我的评论不再有效。请参阅以下答案:https://*.com/a/31443898/109561


I'm guessing you're worried about the distribution of mt_rand(). I have tested it and it is very level and both bounds are inclusive.

我猜你担心mt_rand()的分布。我测试了它,它非常水平,两个边界都是包容性的。

I added my test to the comments of the documentation for mt_rand() on the php manual, but it was removed by a silly moderator due to politics that are too long winded to go into here.

我在php手册中将我的测试添加到了mt_rand()文档的注释中,但由于政治太长,无法进入此处,因此被一位愚蠢的主持人删除了。

#9


1  

If you don't like PHP's built in rand(), you probably shouldn't use their built-in shuffle() either, since it seems to be built on their rand().

如果你不喜欢PHP的内置rand(),你可能也不应该使用他们的内置shuffle(),因为它似乎是在他们的rand()上构建的。

I am halfway sure the "industry standard" shuffle now is the Fisher-Yates shuffle.

我有一半确定现在的“行业标准”洗牌是费雪耶茨洗牌。

#10


1  

There is no such thing as a "perfect" random number. No matter what subjective definition of "perfect" you have. You can only achieve pseudo-random.

没有“完美”的随机数这样的东西。无论你有什么主观的“完美”定义。你只能实现伪随机。

I was simply trying to point you in the right direction. You asked a question about perfect random numbers, even if perfect was in quotes. And yes, you can improve randomness. You can even implement heuristic or "natural" algorithms, such ideas like "atmospheric noise" -- but still, you're not perfect, not by any means.

我只是想指出你正确的方向。你问了一个关于完美随机数的问题,即使是完美的引号。是的,你可以改善随机性。你甚至可以实现启发式或“自然”算法,比如“大气噪声”这样的想法 - 但是,你并不是完美的,不是任何方式。

#11


1  

use /dev/ramdom (linux device true random number generator) to seed mt_rand

使用/ dev / ramdom(linux device true random number generator)来播种mt_rand

<?
$rnd_dev=mcrypt_create_iv(4, MCRYPT_DEV_RANDOM); //need "apt-get install php5-mcrypt"
$seed=ord(substr($rnd_dev, 0, 1))<<24 |
      ord(substr($rnd_dev, 1, 1))<<16 |
      ord(substr($rnd_dev, 2, 1))<<8 |
      ord(substr($rnd_dev, 3, 1));
mt_srand($seed);
echo mt_rand();
?>

#12


0  

I made a PHP class for generating random numbers and strings PHPRandomValue

我创建了一个PHP类来生成随机数和字符串PHPRandomValue

It uses "mcrypt_create_iv(4, MCRYPT_DEV_URANDOM)" to generate random numbers and values. I made it while working on a crypto project because I needed a safe random value generator. Here's an example usage

它使用“mcrypt_create_iv(4,MCRYPT_DEV_URANDOM)”来生成随机数和值。我在加密项目时做了这个,因为我需要一个安全的随机值生成器。这是一个示例用法

$randomValue = new RandomValue;

$randomValue->randomNumber(): = -3880998

$randomValue->randomNumberBetween(1,10): = 2

$randomValue->randomTextString(): = CfCkKDHRgUULdGWcSqP4

$randomValue->randomTextString(10):  = LorPIxaeEY

$randomValue->randomKey(): = C7al8tX9.gqYLf2ImVt/!$NOY79T5sNCT/6Q.$!.6Gf/Q5zpa3

$randomValue->randomKey(10):  = RDV.dc6Ai/

#13


-1  

It is not possible to generate true random numbers, the best you can hope for is pseudo-random which is what rand() provides, your function is no closer to random then rand(). Take a look at this http://en.wikipedia.org/wiki/Random_number_generator

不可能生成真正的随机数,你可以期望的最好是伪随机,这是rand()提供的,你的函数不再接近随机然后rand()。看看这个http://en.wikipedia.org/wiki/Random_number_generator

#14


-1  

Tru Random numbers

Tru随机数

<?php
for ($i = -1; $i <= 4; $i++) {
    $bytes = openssl_random_pseudo_bytes($i, $cstrong);
    $hex   = bin2hex($bytes);

    echo "Lengths: Bytes: $i and Hex: " . strlen($hex) . PHP_EOL;
    var_dump($hex);
    var_dump($cstrong);
    echo PHP_EOL;
}
?>

and also crypto secure ;)

并且加密安全;)

#15


-2  

Although the answer was accepted years ago, I'll re-reopen it.

虽然答案在几年前就被接受了,但我会重新打开它。

Since all this randomness depends on the system time, let's mess with the system time too! The amount of time an operation takes on the computer is actually rather variable (especially if other stuff is happening on that server), so if we take advantage of that with microtime... (couldn't find any portable nanotime commands)

由于所有这些随机性取决于系统时间,让我们也搞乱系统时间!操作在计算机上花费的时间实际上是相当可变的(特别是如果在该服务器上发生其他事情),所以如果我们利用microtime的那个...(找不到任何便携式纳米级命令)

$a='';
for (int $i=0; $i<9001; $i++)
{
    usleep(mt_rand(1000,10000));//Also eliminates timing attacks... possibly?
    $a=hash('SHA512',$a.uniqid(mt_rand().microtime(),true));
}
echo $a;

Nominally this has 207023 bits of entropy, since you're adding another 23 bits every iteration, but there's a lot of interdependencies, so it's probably a few orders of magnitude less. Still pretty good.

名义上它有207023位的熵,因为你每次迭代都会增加23位,但是它有很多相互依赖性,所以它可能要少几个数量级。还不错。

Do you know of any operations on PHP that take a really random amount of time? Like... HTTP-requesting some website (other than RANDOM.org) and measuring the time it takes?

你知道PHP上的任何操作需要花费很多时间吗?就像...... HTTP请求一些网站(RANDOM.org除外)并测量所需的时间?

#16


-4  

Using random.org, you can use this:

使用random.org,您可以使用:

function getToken($length, $min, $max){
    $r = explode('
',file_get_contents('http://www.random.org/integers/num='.$length.'&min='.$min.'&max='.$max.'&col=1&base=10&format=plain'));

    $string = '';
    foreach ( $r as $char ) $string.=$char;
    return $string;
}

this should give real random numbers

这应该给出真正的随机数