r - R:根据最后一次调用的输出递归地指定函数的输入
问题描述
我希望从有界范围 [a, b] 中选择一系列随机样本,其中b
递归地替换为先前采样中绘制的值。
所以,假设我在第一轮从 [0.01, 0.1] 中抽取 0.07,那么我想在下一轮从 [0.01, 0.07] 中抽取。如果现在我绘制 0.033,那么我希望下一次绘制在 [0.01, 0.33] 范围内。为简单起见,假设我希望随机抽取在每次迭代中均匀分布。
参数应该是要进行的抽奖次数,例如 10、100、1000 等。最有效的方法是什么?理想情况下使用一些函数式编程细节。
编辑:
这是一个紧跟斐波那契递归示例的函数:
get_rand_1 = function(n, lower = 0.001, upper = 0.1) {
if(n == 1) return(runif(1, lower, upper))
return(runif(1, 0.01, get_rand_1(n-1, lower, upper)))
}
set.seed(1234567)
sapply(1:10, get_rand_1)
这确实做了我需要它做的事情,但它确实会NaN
不时产生 s ,如以下输出所示:
> sapply(1:10, get_rand_1)
[1] 0.05666382 0.06759059 NaN 0.01245241 0.01019525 0.01117497 0.01096470 0.01001802
[9] 0.01005574 0.01001110
Warning messages:
1: In runif(1, 0.01, get_rand_1(n - 1, lower, upper)) : NAs produced
2: In runif(1, 0.01, get_rand_1(n - 1, lower, upper)) : NAs produced
我不确定这是否是种子的产物,或者这是否是程序的固有缺陷或两者兼而有之。
具体来说,如果我硬编码上限和下限并且不将它们作为参数传递,则不会发生这种情况。
get_rand = function(n) {
if(n == 1) return(runif(1, 0.001, 0.1))
return(runif(1, 0.001, get_rand(n-1)))
}
set.seed(1234567)
sapply(1:10, get_rand)
这会产生:
> set.seed(1234567)
> sapply(1:10, get_rand)
[1] 0.056663823 0.066827837 0.002083137 0.004200264 0.001238414 0.003118070 0.001038515 0.001121686
[9] 0.001084810 0.001020310
这是在 Windows 10 机器上。我可以根据需要提供会话信息。
无论哪种情况,我仍然希望以最有效的方式实现这一点。欢迎提出建议。
解决方案
这是一个基本的方法。几乎可以肯定不是最有效的,但它会起作用。请注意,它倾向于收敛到下限,因为选择的随机数永远不会大于前一个数字。runif(...) 函数从均匀分布中采样。
your_sampler <- function(x, a, b){
temp_list <- c()
temp_list[1] <- runif(1, min = a, max = b)
for(i in 2:x){
temp_list[i] <- runif(1, min = a, max = temp_list[i-1])
}
temp_list
}
# Example
your_sampler(10, 0.3, 10)
推荐阅读
- python - 在列中读取带有换行符的 csv 文件
- google-cloud-platform - 谷歌翻译在特殊字符周围添加空格
- c# - c#如何使洪水填充在颜色渐变上起作用?
- xamarin - 在 XamarinForms 中使用 VisionServiceClient 的各种错误
- c# - 在 B-L072Z-LRWAN1 板 (stm32l0) 的现有 lorawan 项目中添加 adc 配置
- django - 需要帮助形成具有多个聚合的查询集
- python - 循环选择目录中的 x 文件数
- arm-template - Azure VM 映像没有源 Blob URI
- regex - 如何从带有周围字符的 oracle varchar 获取日期时间
- php - 中间件不符合条件 - Laravel 5.7