I want to create a data.frame
which should contain a parameter value (body surface area, BSA). It should be generated in this data.frame
using rnorm()
for 1000 IDs. With
BSA<-data.frame(rep(rnorm(n = 1000, mean = 1.81, sd = 0.2)))
I can easily obtain those values for 1000 IDs. However, I want to have not only 1 but 36 observations per ID. How can I generate the same BSA value based on the above-mentioned mean and SD 36 times for one ID and performing this procedure for 1000 IDs in total?
Unfortunately,
data.frame(rep(rnorm(1, 1.81, 0.2), times=36),times = 1000))
does not work, of course.
EDIT: The output should look like this:
1.89
1.89
1.89
1.67
1.67
1.67
1.74
1.74
1.74
That would be three observations per ID in one column.
EDIT2: The code could look like this:
BSA<-data.frame(c(rep(rnorm(1, 1.81, 0.2), times=36), rep(rnorm(1, 1.81, 0.2), times=36)))
This would generate the desired output for two IDs but it's not very feasible to perform this for 1000 IDs.
You could use cbind
in principle, and draw one rnorm
per each "id"
.
n <- 36 ## 36 IDs
o <- 5 ## 5 observations (change to 1000 in your case)
set.seed(42)
res <- do.call(rbind.data.frame, lapply(1:n, function(i)
cbind(id=i, o=1:o, v=rnorm(1, 1.81, .2))))
res[1:15, ]
# id o v
# 1 1 1 2.084192
# 2 1 2 2.084192
# 3 1 3 2.084192
# 4 1 4 2.084192
# 5 1 5 2.084192
# 6 2 1 1.697060
# 7 2 2 1.697060
# 8 2 3 1.697060
# 9 2 4 1.697060
# 10 2 5 1.697060
# 11 3 1 1.882626
# 12 3 2 1.882626
# 13 3 3 1.882626
# 14 3 4 1.882626
# 15 3 5 1.882626
Or, if you want a vector, mix rep
and replicate
, then c
oncatenate the result,
set.seed(42)
res2 <- do.call(c, replicate(n, rep(rnorm(1, 1.81, .2), o), simplify=F))
even simpler using the each=
argument of rep
(thanks to @Onyambu).
set.seed(42)
res2 <- rep(rnorm(o, 1.81, .2), each=n)
res2[1:15]
# [1] 2.084192 2.084192 2.084192 2.084192 2.084192 1.697060
# [7] 1.697060 1.697060 1.697060 1.697060 1.882626 1.882626
# [13] 1.882626 1.882626 1.882626
To get a data frame, just do as.data.frame(res2)
of course, or something similar.