5

RのA/Bは、行列に対して要素ごとの除算を実行します。

ただし、Matrixパッケージからスパース行列を生成し、A / Bを分割しようとすると、次のエラーが発生します。

> class(N)
[1] "dgCMatrix"
attr(,"package")
[1] "Matrix"
> N/N
Error in asMethod(object) : 
  Cholmod error 'problem too large' at file ../Core/cholmod_dense.c, line 105
> 

面白い。スパース行列の合計サイズが小さい場合、次の動作が発生します。

> m <- sparseMatrix(i=c(1,2,1,3), j=c(1,1,3,3), x=c(1,2,1,4))
> m/m
3 x 3 Matrix of class "dgeMatrix"
     [,1] [,2] [,3]
[1,]    1  NaN    1
[2,]    1  NaN  NaN
[3,]  NaN  NaN    1
> 

しかし、適度なサイズ(〜20000要素)の場合、Cholmodエラーが発生します。

Rのスパース行列で要素ごとの除算を行うための回避策またはより適切な方法はありますか?

4

1 に答える 1

8

要素ごとの分割の問題は、行列が両方ともスパースである場合、結果に多くのInfとが含まNaNれることになり、これらによって行列が密になることです。そのため、メモリ不足エラーが発生します。

Inf結果のゼロを置き換えたい場合NaN、解決策は比較的簡単です。summary()両方の行列を取得し、インデックスと値を直接操作するだけです。

ABインデックスベクトルをそれらの交点に制限し、その上で除算を実行する必要があります。インデックスペアの共通部分を取得するには、を使用できますmerge()

これが迅速で汚い実装です:

# Some example data
A <- sparseMatrix(i=c(1,1,2,3), j=c(1,3,1,3), x=c(1,1,2,3))
B <- sparseMatrix(i=c(3,2,1), j=c(3,2,1), x=c(3,2,1))

sdiv <- function(X, Y, names=dimnames(X)) {
  sX <- summary(X)
  sY <- summary(Y)
  sRes <- merge(sX, sY, by=c("i", "j"))
  sparseMatrix(i=sRes[,1], j=sRes[,2], x=sRes[,3]/sRes[,4],
               dimnames=names)
}

sdiv(A, B)
# 3 x 3 sparse Matrix of class "dgCMatrix"
#           
# [1,] 1 . .
# [2,] . . .
# [3,] . . 1

summaryとの使用について提案してくれたflodelに感謝しmergeます。

于 2012-09-29T04:44:15.750 に答える