在R中使用循环(可能使用paste函数)创建多个矩阵

3

我想创建27个带有2列和可变行数的矩阵。我可以像下面这样写27行代码:

 x1 = cbind(rep(1,34), rnorm(34))

 x2 = cbind(rep(1,36), rnorm(36))

....

x27 = cbind(rep(1,k), rnorm(k))

今日免费次数已满, 请开通会员/明日再来
aux = c(34, 36, ..., k) # auxiliar variable with number of rows for each matrix

for (i in 1:27) paste("x",i, sep="") =  cbind(rep(1,aux[i]), rnorm(aux[i]))

然而,它并没有起作用。我觉得这是一个简单的任务,但是我已经没有了想法。
有什么帮助吗?
附注:我考虑过使用数组,但我无法使用它。也许列表可以完成这项工作,我不知道。

对我来说,创建27个R对象(x1,x2,x3,...,x27)似乎很重要。 - Manoel Galdino
请查看@Joshua Ulrich的答案,因为我觉得我可能误解了你的问题。如果您需要不同的矩阵而不是连接到列表中,则绿色复选标记应该给他。 - daroczig
两种解决方案都可以。谢谢大家,我选择了你的答案(@daroczig),因为它对我有效。 - Manoel Galdino
4个回答

7
你需要使用assign
for (i in 1:27) {
  assign(paste("x",i,sep=""), cbind(rep(1,aux[i]), rnorm(aux[i])))
}

这将在您的全局环境中创建27个矩阵对象。

3
如果您需要不同数量的行,则一定需要使用列表。请参考以下示例:
首先,声明一个变量aux,它保存要生成的行数:
aux <- 50:77

让你的循环继续运转:

x <- vector("list",27) 
for (i in 1:27) {
    x[[i]] <- cbind(rep(1,aux[i]), rnorm(aux[i]))
}

这将返回您的数据框列表。例如,使用str(x)可以查看列表,使用str(x[[1]])可以查看第一个矩阵的结构。后者将返回:

 num [1:50, 1:2] 1 1 1 1 1 1 1 1 1 1 ...

您是正确的:这个提案可以写得更好,可以使用lapply等方式来改进,但其他人会帮助您解决这个棘手的部分 :)


编辑后: 添加了lapply示例

如果您熟悉上面的循环(当然要查找?lapply),请尝试下面的代码:

aux <- 50:77
fun <- function(x) cbind(rep(1,x), rnorm(x))
x <- lapply(aux, fun)

但是你不需要先创建x吗?像x <- list()或x <- vector()这样的东西?在我的电脑上它找不到对象x。 - Manoel Galdino
是的,我们需要先创建x。非常感谢。我使用了简单的x <- list()。 - Manoel Galdino
@Manoel Galdino:是的,对不起这个错误!我已经编辑了我的答案并添加了额外的行,还使用lapply添加了一个示例,以便更好地解决问题 :) - daroczig
2
提前分配内存!在循环之前定义 x <- vector("list",27) 然后在循环中设置 x 的每个元素。这比为每次迭代扩展列表要高效得多。 - Joshua Ulrich
@Joshua Ulrich:没错,谢谢你指出来 - 非常有用。我已经编辑了我的答案,使它更好。而且在阅读你的答案后,我意识到我可能也误解了问题 :( - daroczig
@daroczig:在说它更有效率之后,我决定测试一下我的说法。虽然只是稍微更有效率,但这仍然是一个好的实践。;-) - Joshua Ulrich

2
如果您不反对列表,这里有另一个关于您问题的解答:
aux <- 30:40
manoel <- sapply(aux, function(x) {
            matrix(NA, ncol = 2, nrow = x)
        }, simplify = FALSE)

> str(manoel)
List of 11
 $ : logi [1:30, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:31, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:32, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:33, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:34, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:35, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:36, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:37, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:38, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:39, 1:2] NA NA NA NA NA NA ...
 $ : logi [1:40, 1:2] NA NA NA NA NA NA ...

1
下面的代码展示了我如何使用Joshua Ulrich的方法创建稍微复杂一些的矩阵。希望这个答案有助于展示创建对象时可能存在的灵活性。如果没有,我可以删除我的回答。
我怀疑这种方法可以轻松修改以创建大小不同的矩阵,例如,通过将nrow或ncol设置为变量,并在matrix或rbind语句中使用rep(q, z)和某个变量z来复制向量中的元素。
p1.c1 <- 0.10
p2.c1 <- 0.20
p3.c1 <- 0.30
p4.c1 <- 0.40

s1.c1  <- matrix(c(p1.c1, p1.c1, (1 - p1.c1),
                   p1.c1, p1.c1, (1 - p1.c1),
                       0,     0,          1), nrow=3, ncol=3, byrow = TRUE)
s2.c1  <- matrix(c(p2.c1, p2.c1, (1 - p2.c1),
                   p2.c1, p2.c1, (1 - p2.c1),
                       0,     0,          1), nrow=3, ncol=3, byrow = TRUE)
s3.c1  <- matrix(c(p3.c1, p3.c1, (1 - p3.c1),
                   p3.c1, p3.c1, (1 - p3.c1),
                       0,     0,          1), nrow=3, ncol=3, byrow = TRUE)
s4.c1  <- matrix(c(p4.c1, p4.c1, (1 - p4.c1),
                   p4.c1, p4.c1, (1 - p4.c1),
                       0,     0,          1), nrow=3, ncol=3, byrow = TRUE)

n <- 5

p.c1 <- c(p1.c1, p2.c1, p3.c1, p4.c1)

for (i in 1: (n - 1)) {
  assign(paste('xs', i, '.c1', sep=""), matrix(c(p.c1[i], p.c1[i], (1-p.c1[i]),
                                                 p.c1[i], p.c1[i], (1-p.c1[i]),
                                                       0,       0,         1 ), nrow=3, ncol=3, byrow = TRUE))
}
identical(xs1.c1, s1.c1)
identical(xs2.c1, s2.c1)
identical(xs3.c1, s3.c1)
identical(xs4.c1, s4.c1)

for (i in 1: (n - 1)) {
  assign(paste('ys', i, '.c1', sep=""), rbind(c(p.c1[i], p.c1[i], (1-p.c1[i])),
                                              c(p.c1[i], p.c1[i], (1-p.c1[i])),
                                                    c(0,       0,          1)))

}
identical(ys1.c1, s1.c1)
identical(ys2.c1, s2.c1)
identical(ys3.c1, s3.c1)
identical(ys4.c1, s4.c1)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接