我有一个矩阵,其元素是0,1,2,NA!
我想删除其colsums等于0或NA的列!我想从原始矩阵中删除这些列,并为这些列创建一个新矩阵(非零colsums)!(我认为在计算colsums时我考虑了na.rm = True并删除colsum = 0的colums,因为如果我认为na.rm = False,我的colsums的所有值都得到NA)
这是我的矩阵格式:
mat[1:6,1:6]
1:11059017 1:11088817 1:11090640 1:11099385 1:1109967 1:111144756
0 0 0 0 NA 0
0 0 0 0 0 NA
1 NA 2 0 NA 0
0 0 0 1 0 2
2 0 0 0 0 0
0 0 NA 0 0 0
Summat <- colSums(mat,na.rm = TRUE)
head(summat)
1:11059017 1:11088817 1:11090640 1:11099385 1:1109967 1:111144756
[,1] 3 0 2 1 0 2
Run Code Online (Sandbox Code Playgroud)
第2列和第5列有colsum = 0所以我应该从met中删除它们并将其余列保留在另一个矩阵中.
我的输出应该如下:
met-nonzero
1:11059017 1:11090640 1:11099385 1:111144756
0 0 0 0
0 0 0 NA
1 2 0 0
0 0 1 2
2 0 0 0
0 NA 0 0
Run Code Online (Sandbox Code Playgroud)
你能让我知道我该怎么办?
数据:
structure(c(0L, 0L, 1L, 0L, 2L, 0L, 0L, 0L, NA, 0L, 0L, 0L, 0L,
0L, 2L, 0L, 0L, NA, 0L, 0L, 0L, 1L, 0L, 0L, NA, 0L, NA, 0L, 0L,
0L, 0L, NA, 0L, 2L, 0L, 0L), .Dim = c(6L, 6L), .Dimnames = list(
NULL, c("X1.11059017", "X1.11088817", "X1.11090640", "X1.11099385",
"X1.1109967", "X1.111144756")))
Run Code Online (Sandbox Code Playgroud)
谢谢
弄清楚哪些有colSums != 0:
i <- (colSums(mat, na.rm=T) != 0) # T if colSum is not 0, F otherwise
Run Code Online (Sandbox Code Playgroud)
然后你可以选择或删除它们,例如
matnonzero <- mat[, i] # all the non-zero columns
matzeros <- mat[, !i] # all the zero columns
Run Code Online (Sandbox Code Playgroud)
更新评论(没有方法可以做到这一点colSums).IMO,是的,但是,colSums是更优雅/更有效的方式之一.
你可以这样做:
apply(is.na(mat) | mat == 0, 2, all)
Run Code Online (Sandbox Code Playgroud)
对于全NA/0的每列,它将返回TRUE,这样
mat[, !apply(is.na(mat) | mat == 0, 2, all)]
Run Code Online (Sandbox Code Playgroud)
将返回所有非零列.
然而colSums比快apply.
system.time( replicate(1000, mat[, !apply(is.na(mat) | mat == 0, 2, all)]) )
# user system elapsed
# 0.068 0.000 0.069
system.time( replicate(1000, mat[, colSums(mat, na.rm=T) != 0]))
# user system elapsed
# 0.012 0.000 0.013
Run Code Online (Sandbox Code Playgroud)
我确信还有很多其他方法可以做到这一点.
再次更新,因为OP不断在评论中添加他们的问题.新问题是:删除所有列:
机制没有改变 - 你只需要为每一列决定是否保留它的布尔值(true或false).
例如
就像如果all在一列中的值is.na或者==0您删除列,与你的第二个条件,你可以写(EG) length(unique({column})) == 1,或all(diff({column})) == 0,或许多其他等效方法.
所以要结合它们,请记住apply(X, 2, FUN)将函数FUN应用于每一列X.
所以你可以这样做:
i <- apply(mat,
2,
function (column) {
any(is.na(col) | col == 0) |
length(unique(col)) == 1
})
Run Code Online (Sandbox Code Playgroud)
它返回TRUE如果列具有任何NAS或0,或如果整个列仅具有一个唯一的值.所以这就是TRUE我们应该丢弃该列.然后像以前一样对矩阵进行子集化,即
mat[, !i]
Run Code Online (Sandbox Code Playgroud)
如果您希望添加与您已经要求的条件不同的其他条件,请仔细考虑并自己尝试,如果您仍然不能,请提出一个新问题,而不是再次修改此问题.
| 归档时间: |
|
| 查看次数: |
5862 次 |
| 最近记录: |