设置 rnorm 参数等于向量
Set rnorm parameters equal to vector
我有一个数据框,其中包含样本大小、均值和标准差的列,以及一个 target
值:
ssize <- c(200, 300, 150)
mean <- c(10, 40, 50)
sd <- c(5, 15, 65)
target <- c(7, 23, 30)
df <- data.frame(ssize, mean, sd, target)
我想添加另一个变量 below
,即 returns 小于 target
值的元素数量,从具有参数 mean
和sd
和样本大小 ssize
。但是,我无法让 rnorm
将每行的值用作参数。例如,运行宁
df$below <- sum(rnorm(df$ssize, df$mean, df$sd) < df$target)
生成样本大小等于 length(df$ssize)
而不是 df$ssize
本身的值的分布。
已更新:数据 table 大型数据集的解决方案?
@alistaire 和@G5W 的解决方案效果很好,但我想从每行的 100 个 rnorm 副本中提取 below
的平均值。我尝试了两种解决方案:
df <- df %>% mutate(below = mean(replicate(100, pmap_int(., ~sum(rnorm(..1, ..2, ..3) < ..4)))))
df$below <- with(df, sapply(1:nrow, function(i) mean(replicate(100, sum(rnorm(n[i], mean[i], sd[i]) < target[i])))))
但是他们需要很长时间才能 运行 我的数据集,它有超过 430 万行。是否有可能更快的数据 table(或其他)解决方案?
列表列是执行此操作的自然方式,因此您可以将示例存储在生成它们的参数旁边。使用 purrr 进行迭代,
library(tidyverse)
set.seed(47) # for reproducibility
df <- data_frame(n = c(200, 300, 150), # rename to name of parameter in rnorm so pmap works naturally
mean = c(10, 40, 50),
sd = c(5, 15, 65),
target = c(7, 23, 30))
df %>%
mutate(samples = pmap(.[1:3], rnorm), # iterate in parallel over parameters and store samples as list column
below = map2_int(samples, target, ~sum(.x < .y))) # iterate over samples and target, calculate number below, and simplify to integer vector
#> # A tibble: 3 x 6
#> n mean sd target samples below
#> <dbl> <dbl> <dbl> <dbl> <list> <int>
#> 1 200 10 5 7 <dbl [200]> 47
#> 2 300 40 15 23 <dbl [300]> 41
#> 3 150 50 65 30 <dbl [150]> 58
你可以在 base R 中使用 lapply
和一个临时函数
df$below = with(df,
sapply(1:3, function(i) sum(rnorm(ssize[i], mean[i], sd[i]) < target[i])))
df$below
[1] 44 45 48
我有一个数据框,其中包含样本大小、均值和标准差的列,以及一个 target
值:
ssize <- c(200, 300, 150)
mean <- c(10, 40, 50)
sd <- c(5, 15, 65)
target <- c(7, 23, 30)
df <- data.frame(ssize, mean, sd, target)
我想添加另一个变量 below
,即 returns 小于 target
值的元素数量,从具有参数 mean
和sd
和样本大小 ssize
。但是,我无法让 rnorm
将每行的值用作参数。例如,运行宁
df$below <- sum(rnorm(df$ssize, df$mean, df$sd) < df$target)
生成样本大小等于 length(df$ssize)
而不是 df$ssize
本身的值的分布。
已更新:数据 table 大型数据集的解决方案?
@alistaire 和@G5W 的解决方案效果很好,但我想从每行的 100 个 rnorm 副本中提取 below
的平均值。我尝试了两种解决方案:
df <- df %>% mutate(below = mean(replicate(100, pmap_int(., ~sum(rnorm(..1, ..2, ..3) < ..4)))))
df$below <- with(df, sapply(1:nrow, function(i) mean(replicate(100, sum(rnorm(n[i], mean[i], sd[i]) < target[i])))))
但是他们需要很长时间才能 运行 我的数据集,它有超过 430 万行。是否有可能更快的数据 table(或其他)解决方案?
列表列是执行此操作的自然方式,因此您可以将示例存储在生成它们的参数旁边。使用 purrr 进行迭代,
library(tidyverse)
set.seed(47) # for reproducibility
df <- data_frame(n = c(200, 300, 150), # rename to name of parameter in rnorm so pmap works naturally
mean = c(10, 40, 50),
sd = c(5, 15, 65),
target = c(7, 23, 30))
df %>%
mutate(samples = pmap(.[1:3], rnorm), # iterate in parallel over parameters and store samples as list column
below = map2_int(samples, target, ~sum(.x < .y))) # iterate over samples and target, calculate number below, and simplify to integer vector
#> # A tibble: 3 x 6
#> n mean sd target samples below
#> <dbl> <dbl> <dbl> <dbl> <list> <int>
#> 1 200 10 5 7 <dbl [200]> 47
#> 2 300 40 15 23 <dbl [300]> 41
#> 3 150 50 65 30 <dbl [150]> 58
你可以在 base R 中使用 lapply
和一个临时函数
df$below = with(df,
sapply(1:3, function(i) sum(rnorm(ssize[i], mean[i], sd[i]) < target[i])))
df$below
[1] 44 45 48