需要在R中编写一个新的随机生成器

时间:2018-09-16 16:55:39

标签: r random

我需要生成-1,1之间的7个随机数,它们的总和等于1。我使用此代码来这样做。

 diff(c(0, sort(round(runif(7,-1,1),2)), 1))

但是我对此有很大的疑问。

此代码的一个输出为 -0.89、0.21、0.00、0.21、0.30、0.19、0.61,-0.63

问题是我想这是统一的,所以每次在我不想使用的第一个和最后一个数字中都生成大随机数。我需要将其传播到所有数字。 例如 0.22 -.21 .33 -.12 0.11 0.35 -0.08 (总和不等于1只是一个例子)

您知道谁可以编写代码来获得这种随机数吗?

3 个答案:

答案 0 :(得分:5)

您的一般想法可能是受说明中链接的答案的启发。标准问题是如何生成0到1之间的7个加到1的数字。答案是:

diff(c(0, sort(runif(6, 0, 1)), 1))
#> [1] 0.27960792 0.02035231 0.02638626 0.09945877 0.25134002 0.03379598 0.28905874

获取介于-1和1之间的数字的必要修改非常简单;只需删除sort

diff(c(0, runif(6, 0, 1), 1))
#> [1]  0.9961661 -0.6528227  0.5298829 -0.2087127 -0.2298045  0.2017705  0.3635203

这是如何工作的?我们再次在零和一之间划分空间。但是b省略了排序,我们考虑了倒退的可能性,即负数是可能的。这是1000代的直方图:

enter image description here

此方法的一个缺点是,第一个和最后一个数字必须为正。如果您对此感到困扰,则可以添加其他sample,例如:

sample(diff(c(0, runif(6, 0, 1), 1)), 7)
#> [1] -0.004242793 -0.725348335  0.385971491  0.320525822  0.389915347
#> [6]  0.053195271  0.579983197

答案 1 :(得分:2)

可能有2个解决方案,并且它们都可以在无限循环中工作:

解决方案1:

您可以考虑6个随机数,以及1个相关数,因此它们的总和可以为1。但是,可能会发生一个元素大于1或小于-1的情况。因此,我们不能接受所有答案。

while(T){
  res<-runif(6,-1,1)

  res<-append(res,1-sum(res))

  if(sum(res>1)==0)
    break
}

res

输出为:

-0.34038038  0.15811401 -0.20748670  0.26443104  0.45216639 -0.09912685  0.77228248

解决方案2:

我们应该继续产生不同的结果,并希望获得正确的答案。但是,为了减少时间,我们必须将随机数舍入一位数字

while(T){
  res<-round(runif(7,-1,1), digits = 1)
  print(sum(res))
  if(sum(res)==1)

     break

  }

res

输出:

> res
[1] -0.6  0.2  0.4  0.7 -0.2  0.6 -0.1

答案 2 :(得分:0)

类似的解决方案,例如Salman Lashkarara。您应该将数字四舍五入以找到解决方案。

library(magrittr)

set.seed(42)
x <- 1

while(sum(x) != 0){
  x <- runif(7,-1,1) %>%
    round(3)
}

x
#> [1]  0.155  0.559 -0.335 -0.230 -0.490 -0.557  0.898
sum(x)
#> [1] 0

Created on 2018-09-16 by the [reprex package](http://reprex.tidyverse.org) (v0.2.0).