在 R 中的循环中使用开始值和结束值的示例
Sample using start and end values within a loop in R
我正在尝试在一系列值之间进行采样,作为 R 中较大循环的一部分。随着循环进行到每一行 j
,我想在 start
列和 end
列中给出的值,将该值放在该行的 sampled
列中。
结果应如下所示:
ID start end sampled
a 25 67 44
b 36 97 67
c 23 85 77
d 15 67 52
e 21 52 41
f 43 72 66
g 39 55 49
h 27 62 35
i 11 99 17
j 21 89 66
k 28 65 48
l 44 58 48
m 16 77 22
n 25 88 65
我开始使用 mapply
,它对整个 df 进行采样,但后来我试图将所有 15 个采样值放入一行。
df[j,4] <- mapply(function(x, y) sample(seq(x, y), 1), df$start, df$end)
我想也许使用 seq
的东西可能会起作用,但这会导致错误提示 from
的长度必须为 1。
df[j,4] <- sample(seq(df$start, df$end),1,replace=TRUE)
外部循环结构非常复杂,因此我没有在此处包含它,但是代码的 df[j,4]
部分是必需的,因为它是更大循环的一部分。在某些情况下,必须根据实际数据集中的其他依赖项对行进行重新采样。例如,a
的采样值可能需要大于 b
。其余代码更新采样列,检查依赖项,如果不满足依赖项,将重新运行示例。如果我能让这个采样部分工作,我应该可以毫不费力地插入它(我希望)。
这是一个示例数据集。
structure(list(ID = c("a", "b", "c", "d", "e", "f", "g", "h",
"i", "j", "k", "l", "m", "n"), start = c(25, 36, 23, 15, 21,
43, 39, 27, 11, 21, 28, 44, 16, 25), end = c(67, 97, 85, 67,
52, 72, 55, 62, 99, 89, 65, 58, 77, 88), sampled = c(NA, NA,
NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA)), class = c("spec_tbl_df",
"tbl_df", "tbl", "data.frame"), row.names = c(NA, -14L), spec = structure(list(
cols = list(ID = structure(list(), class = c("collector_character",
"collector")), start = structure(list(), class = c("collector_double",
"collector")), end = structure(list(), class = c("collector_double",
"collector")), sampled = structure(list(), class = c("collector_logical",
"collector"))), default = structure(list(), class = c("collector_guess",
"collector")), skip = 1), class = "col_spec"))```
首先,将数据置于更易于与dput(df)
一起使用的格式:
df <- structure(list(ID = structure(1:14, .Label = c("a", "b", "c",
"d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n"), class = "factor"),
start = c(25L, 36L, 23L, 15L, 21L, 43L, 39L, 27L, 11L, 21L,
28L, 44L, 16L, 25L), end = c(67L, 97L, 85L, 67L, 52L, 72L,
55L, 62L, 99L, 89L, 65L, 58L, 77L, 88L), sampled = c(44L,
67L, 77L, 52L, 41L, 66L, 49L, 35L, 17L, 66L, 48L, 48L, 22L,
65L)), class = "data.frame", row.names = c(NA, -14L))
你与 mapply()
非常接近,但你让它变得比需要的更难:
df$sampled <- mapply(function(x, y) sample(seq(x, y), 1), df$start, df$end)
df
# ID start end sampled
# 1 a 25 67 67
# 2 b 36 97 86
# 3 c 23 85 54
# 4 d 15 67 36
# 5 e 21 52 37
# 6 f 43 72 60
# 7 g 39 55 44
# 8 h 27 62 37
# 9 i 11 99 86
# 10 j 21 89 52
# 11 k 28 65 65
# 12 l 44 58 51
# 13 m 16 77 62
# 14 n 25 88 31
您可能不需要循环。如果你想要的是介于开始和结束之间的东西,它几乎等同于对 0-1 之间的东西进行采样并将其乘以范围。
df %>% mutate(sampled = start + round((end-start)*runif(nrow(.))))
关于更新,您在评论中提到的依赖项:听起来有点复杂。
快速思考:可能会更快地采样很多次并选择一个符合您标准的。
想通了。
df[j,4] <- mapply(function(x, y) sample(seq(x, y), 1), df[j,"start"], df[j,"end"])
我只需要具体说明我想输入哪一行采样值 df[j,4]
。为列 start
和 end
指定行 j
就可以了。
我正在尝试在一系列值之间进行采样,作为 R 中较大循环的一部分。随着循环进行到每一行 j
,我想在 start
列和 end
列中给出的值,将该值放在该行的 sampled
列中。
结果应如下所示:
ID start end sampled
a 25 67 44
b 36 97 67
c 23 85 77
d 15 67 52
e 21 52 41
f 43 72 66
g 39 55 49
h 27 62 35
i 11 99 17
j 21 89 66
k 28 65 48
l 44 58 48
m 16 77 22
n 25 88 65
我开始使用 mapply
,它对整个 df 进行采样,但后来我试图将所有 15 个采样值放入一行。
df[j,4] <- mapply(function(x, y) sample(seq(x, y), 1), df$start, df$end)
我想也许使用 seq
的东西可能会起作用,但这会导致错误提示 from
的长度必须为 1。
df[j,4] <- sample(seq(df$start, df$end),1,replace=TRUE)
外部循环结构非常复杂,因此我没有在此处包含它,但是代码的 df[j,4]
部分是必需的,因为它是更大循环的一部分。在某些情况下,必须根据实际数据集中的其他依赖项对行进行重新采样。例如,a
的采样值可能需要大于 b
。其余代码更新采样列,检查依赖项,如果不满足依赖项,将重新运行示例。如果我能让这个采样部分工作,我应该可以毫不费力地插入它(我希望)。
这是一个示例数据集。
structure(list(ID = c("a", "b", "c", "d", "e", "f", "g", "h",
"i", "j", "k", "l", "m", "n"), start = c(25, 36, 23, 15, 21,
43, 39, 27, 11, 21, 28, 44, 16, 25), end = c(67, 97, 85, 67,
52, 72, 55, 62, 99, 89, 65, 58, 77, 88), sampled = c(NA, NA,
NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA)), class = c("spec_tbl_df",
"tbl_df", "tbl", "data.frame"), row.names = c(NA, -14L), spec = structure(list(
cols = list(ID = structure(list(), class = c("collector_character",
"collector")), start = structure(list(), class = c("collector_double",
"collector")), end = structure(list(), class = c("collector_double",
"collector")), sampled = structure(list(), class = c("collector_logical",
"collector"))), default = structure(list(), class = c("collector_guess",
"collector")), skip = 1), class = "col_spec"))```
首先,将数据置于更易于与dput(df)
一起使用的格式:
df <- structure(list(ID = structure(1:14, .Label = c("a", "b", "c",
"d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n"), class = "factor"),
start = c(25L, 36L, 23L, 15L, 21L, 43L, 39L, 27L, 11L, 21L,
28L, 44L, 16L, 25L), end = c(67L, 97L, 85L, 67L, 52L, 72L,
55L, 62L, 99L, 89L, 65L, 58L, 77L, 88L), sampled = c(44L,
67L, 77L, 52L, 41L, 66L, 49L, 35L, 17L, 66L, 48L, 48L, 22L,
65L)), class = "data.frame", row.names = c(NA, -14L))
你与 mapply()
非常接近,但你让它变得比需要的更难:
df$sampled <- mapply(function(x, y) sample(seq(x, y), 1), df$start, df$end)
df
# ID start end sampled
# 1 a 25 67 67
# 2 b 36 97 86
# 3 c 23 85 54
# 4 d 15 67 36
# 5 e 21 52 37
# 6 f 43 72 60
# 7 g 39 55 44
# 8 h 27 62 37
# 9 i 11 99 86
# 10 j 21 89 52
# 11 k 28 65 65
# 12 l 44 58 51
# 13 m 16 77 62
# 14 n 25 88 31
您可能不需要循环。如果你想要的是介于开始和结束之间的东西,它几乎等同于对 0-1 之间的东西进行采样并将其乘以范围。
df %>% mutate(sampled = start + round((end-start)*runif(nrow(.))))
关于更新,您在评论中提到的依赖项:听起来有点复杂。 快速思考:可能会更快地采样很多次并选择一个符合您标准的。
想通了。
df[j,4] <- mapply(function(x, y) sample(seq(x, y), 1), df[j,"start"], df[j,"end"])
我只需要具体说明我想输入哪一行采样值 df[j,4]
。为列 start
和 end
指定行 j
就可以了。