我有以下R代码:
CutMatrix <- FullMatrix[, colSums( FullMatrix[-1,] != FullMatrix[-nrow( FullMatrix ), ] ) > 0]
通过查找FullMatrix中的哪些列的唯一值大于1的列,从而采用一个矩阵-FullMatrix并创建一个CutMatrix-因此将消除所有具有相同值的列。我想知道是否可以使用Rcpp加快大型矩阵的速度,但是我不确定做到这一点的最佳方法-是否存在轻松实现此目的的甜味方式(例如,通过遍历cols并计数唯一值的数量),或者如果我不得不使用STL中更复杂的内容。
我以为可能是下面的事情是一个开始(我还没有完全弄清楚)-试图在R函数的colSums大括号之间进行操作,但是我不认为我在设置子对象矩阵正确,因为它不起作用。
src <- '
//Convert the inputted character matrix of DNA sequences an Rcpp class.
Rcpp::CharacterMatrix mymatrix(inmatrix);
//Get the number of columns and rows in the matrix
int ncolumns = mymatrix.ncol();
int numrows = mymatrix.nrow();
//Get the dimension names
Rcpp::List dimnames = mymatrix.attr("dimnames");
Rcpp::CharacterMatrix vec1 = mymatrix(Range(1,numrows),_);
Rcpp::CharacterMatrix vec2 = mymatrix(Range(0,numrows-1),_);
'
uniqueMatrix <- cxxfunction(signature(inmatrix="character"), src, plugin="Rcpp")
谢谢,
本
最佳答案
这将返回一个LogicalVector
,它是所有这些列的FALSE
,只有一个unique
值,您可以使用该子集来子集R matrix
。
require( Rcpp )
cppFunction('
LogicalVector unq_mat( CharacterMatrix x ){
int nc = x.ncol() ;
LogicalVector out(nc);
for( int i=0; i < nc; i++ ) {
out[i] = unique( x(_,i) ).size() != 1 ;
}
return out;
}'
)
您可以像这样使用它...
# Generate toy data
set.seed(1)
mat <- matrix( as.character(c(rep(1,5),sample(3,15,repl=TRUE),rep(5,5))),5)
[,1] [,2] [,3] [,4] [,5]
[1,] "1" "1" "3" "1" "5"
[2,] "1" "2" "3" "1" "5"
[3,] "1" "2" "2" "3" "5"
[4,] "1" "3" "2" "2" "5"
[5,] "1" "1" "1" "3" "5"
mat[ , unq_mat(mat) ]
[,1] [,2] [,3]
[1,] "1" "3" "1"
[2,] "2" "3" "1"
[3,] "2" "2" "3"
[4,] "3" "2" "2"
[5,] "1" "1" "3"
一些基本的基准测试...
applyR <- function(y) { y[ , apply( y , 2 , function(x) length( unique(x) ) != 1L ) ] }
rcpp <- function(x) x[ , unq_mat(x) ]
require(microbenchmark)
microbenchmark( applyR(mat) , rcpp(mat) )
#Unit: microseconds
# expr min lq median uq max neval
# applyR(mat) 131.94 134.737 136.31 139.29 268.07 100
# rcpp(mat) 4.20 4.901 7.70 8.05 13.30 100