关于合并具有不同长度的向量here,存在类似的问题,但是所有答案(@Ronak Shah的答案除外)都使名称/名称失去意义。
我的问题是我需要保留列名,这似乎可以使用rowr
包和cbind.fills
来实现。
我想留在 base-R 或使用stringi
,输出应该仍然是矩阵。
测试数据:
inp <- list(structure(c("1", "2"), .Dim = 2:1, .Dimnames = list(NULL,"D1")),
structure(c("3", "4", "5"), .Dim = c(3L, 1L), .Dimnames = list(NULL, "D2")))
我知道我可以预先获取列名,然后在创建矩阵后重新分配它们,例如:
## Using stringi
colnam <- unlist(lapply(inp, colnames))
out <- stri_list2matrix(inp)
colnames(out) <- colnam
out
## Using base-R
colnam <- unlist(lapply(inp, colnames))
max_length <- max(lengths(inp))
nm_filled <- lapply(inp, function(x) {
ans <- rep(NA, length = max_length)
ans[1:length(x)]<- x
ans
})
out <- do.call(cbind, nm_filled)
colnames(out) <- colnam
out
还有其他保留列名的选项吗?
答案 0 :(得分:2)
由于可以使用stringi
,因此可以使用函数stri_list2matrix()
,即
setNames(as.data.frame(stringi::stri_list2matrix(inp)), sapply(inp, colnames))
# D1 D2
#1 1 3
#2 2 4
#3 <NA> 5
答案 1 :(得分:1)
这是一个稍微简洁的基本R变体
len <- max(lengths(inp))
nms <- sapply(inp, colnames)
do.call(cbind, setNames(lapply(inp, function(x)
replace(rep(NA, len), 1:length(x), x)), nms))
# D1 D2
#[1,] "1" "3"
#[2,] "2" "4"
#[3,] NA "5"
不确定这与您已发布的解决方案是否构成足够不同的解决方案。如果认为过于相似,则将其删除。
还是merge
呢?
Reduce(
function(x, y) merge(x, y, all = T, by = 0),
lapply(inp, as.data.frame))[, -1]
# D1 D2
#1 1 3
#2 2 4
#3 <NA> 5
这里的想法是将list
项转换为data.frame
,然后添加row
和merge
,并加上row
和merge
按行设置by = 0
(感谢@Henrik)。请注意,这将返回data.frame
而不是matrix
。
答案 2 :(得分:0)
这里使用的是基数:
do.call(cbind,
lapply(inp, function(i){
x <- data.frame(i, stringsAsFactors = FALSE)
as.matrix( x[ seq(max(lengths(inp))), , drop = FALSE ] )
#if we matrices have more than 1 column use:
#as.matrix( x[ seq(max(sapply(inp, nrow))), , drop = FALSE ] )
}
))
# D1 D2
# 1 "1" "3"
# 2 "2" "4"
# NA NA "5"
该想法是使所有矩阵具有相同数量的行。当我们按索引子集 dataframe 时,不存在的行将作为NA返回,然后我们转换回矩阵和 cbind 。