简体   繁体   English

从列表子元素列表中提取矩阵,保持矩阵的列表/子列表索引

[英]Extracting matrices from list of list sub-elements keeping the list/sub-list indices for the matrix

New to r and was hoping to find an elegant way of solving what seems like a simple problem. r的新手并希望找到一种解决看似简单问题的优雅方式。 The context of the problem is as follows: I am running regressions for a set of companies at rolling periods of time. 问题的背景如下:我在一段时间内为一组公司运行回归。 I am storing the summary of each regression in a list of lists. 我将每个回归的摘要存储在列表列表中。 So, for example: 所以,例如:

results[[i]][[t]] = summary(lm(y~x)) , where y and x are the associated vectors for company i at time t . results[[i]][[t]] = summary(lm(y~x)) ,其中yx是公司i在时间t的关联向量。 I would like to extract matrices like sigma from results such that: 我想从results提取像sigma这样的矩阵,这样:

sigma[i,t] = results [[i]] [[t]]$sigma

Clearly I can do this with nested loops, but it seems that there must be a simple way of extracting this matrix in one step with something like lapply, sapply, etc. I have seen similar problems answered throughout the web and this blog, but have not been able to correctly adapt them to this problem. 很明显,我可以用嵌套循环来做到这一点,但似乎必须有一个简单的方法,一步提取这个矩阵,如lapply,sapply等。我已经看到在整个网络和这个博客中回答类似的问题,但有无法正确地适应这个问题。 Another twist is some of the entries in results are 'Null', which happens when there is insufficient data for a specific company at a specific time to run the regression. 另一个转折是结果中的一些条目是'Null',当特定公司在特定时间运行回归时没有足够的数据时会发生这种情况。

Any help or direction would be much appreciated. 任何帮助或方向将不胜感激。

You can use lapply and do.call : 你可以使用lapplydo.call

First create some sample data: 首先创建一些示例数据:

results <- list()
for (i in 1:5){
  results[[i]] <- list()
  for (t in 1:3){
    x <- sample(10)
    y <- sample(10)
    results[[i]][[t]] <- summary(lm(x~y))
  }
}

Then create the new matrix with the sigmas: 然后使用sigma创建新矩阵:

sigma <- do.call(rbind, lapply(results, function(x)lapply(x, function(y)y$sigma)))
colnames(sigma) <- paste("t", 1:ncol(sigma), sep="")
rownames(sigma) <- paste("c", 1:nrow(sigma), sep="")

the matrix looks as follows: 矩阵如下:

> sigma
   t1       t2       t3      
c1 2.302831 3.201325 3.154122
c2 3.066436 3.179956 3.146427
c3 2.752409 3.189946 2.819306
c4 3.211249 3.210777 2.983795
c5 3.179956 3.179956 2.340034

或者另一种方式:

sigma <- apply(simplify2array(results),1:2,function(v)v[[1]]$sigma)

And another couple of ways, why not... 另外两种方式,为什么不......

## seed used to generate data
set.seed(1)
sigs <- unlist(results)
sigma <- sigs[ names(sigs) %in% "sigma"]
sigma <- matrix(sigma , length( results ) )
#        [,1]     [,2]     [,3]
#[1,] 3.206527 2.797726 3.100342
#[2,] 3.208417 3.138230 3.138230
#[3,] 2.819306 3.138230 3.201325
#[4,] 3.179956 3.209833 3.194218
#[5,] 2.983795 2.652614 3.174233

Thanks to @user1981275 for providing some reproducible data. 感谢@ user1981275提供一些可重现的数据。

Time is in columns. 时间在列中。

A variation on lapply is to use sapply as it's return is already in the form you require: lapply的变体是使用sapply因为它的返回已经是你需要的形式:

t(sapply( results , function(x) sapply( x , function(y) y$sigma ) ) )
#        [,1]     [,2]     [,3]
#[1,] 3.206527 2.797726 3.100342
#[2,] 3.208417 3.138230 3.138230
#[3,] 2.819306 3.138230 3.201325
#[4,] 3.179956 3.209833 3.194218
#[5,] 2.983795 2.652614 3.174233

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM