2017-12-27 18 views
1

Dies ist ein Beispiel für den Vergleich der Zeilenextraktion aus großen Matrizen, spärlich und dicht, unter Verwendung der Matrix package gegenüber der regulären base-matrix Klasse.Extraktionsgeschwindigkeit im Matrixpaket ist sehr langsam im Vergleich zur regulären Matrixklasse

Für dichte Matrizen der Geschwindigkeit ist fast 395-mal schneller für die Basisklasse matrix:

library(Matrix) 
library(microbenchmark) 

## row extraction in dense matrices 
D1<-matrix(rnorm(2000^2), 2000, 2000) 
D2<-Matrix(D1) 
> microbenchmark(D1[1,], D2[1,]) 
Unit: microseconds 
    expr  min  lq  mean median  uq  max neval 
D1[1, ] 14.437 15.9205 31.72903 31.4835 46.907 75.101 100 
D2[1, ] 5730.730 5744.0130 5905.11338 5777.3570 5851.083 7447.118 100 

Für schwach besetzte Matrizen es fast 63 Mal für matrix wieder an ist.

## row extraction in sparse matrices 
S1<-matrix(1*(runif(2000^2)<0.1), 2000, 2000) 
S2<-Matrix(S1, sparse = TRUE) 
microbenchmark(S1[1,], S2[1,]) 
Unit: microseconds 
    expr  min  lq  mean median  uq  max neval 
S1[1, ] 15.225 16.417 28.15698 17.7655 42.9905 45.692 100 
S2[1, ] 1652.362 1670.507 1771.51695 1774.1180 1787.0410 5241.863 100 

Warum die Geschwindigkeit Diskrepanz, und ist es eine Möglichkeit, Extraktion in Matrix Paket zu beschleunigen?

Antwort

1

Ich weiß nicht genau, was das Problem ist, möglicherweise S4-Versand (was möglicherweise ein großes Stück eines kleinen Anrufs wie folgt sein könnte). Ich war in der Lage, Leistung zu erhalten, die matrix entspricht (die einen ziemlich einfachen Job hat, indizierend + auf einen zusammenhängenden Chunk des Gedächtnisses zugreifend), indem (1) zu einem Reihe-Hauptformat und zu schreiben (2) meine spezielle zweckspezifische Accessorfunktion schreibt. Ich weiß nicht genau, was Sie tun möchten, oder ob es die Mühe wert sein wird ...

Beispiel ein:

set.seed(101) 
S1 <- matrix(1*(runif(2000^2)<0.1), 2000, 2000) 

Umrechnen in column-major (dgCMatrix) und Reihe-Dur (dgRMatrix) Formen:

library(Matrix) 
S2C <- Matrix(S1, sparse = TRUE) 
S2R <- as(S1,"dgRMatrix") 

Individuelle Accessor:

my_row_extract <- function(m,i=1) { 
    r <- numeric(ncol(m)) ## set up zero vector for results 
    inds <- seq([email protected][i]+1,[email protected][i+1]) ## find indices 
    r[[email protected][inds]+1] <- [email protected][inds]  ## set values 
    return(r) 
} 

prüfen Gleichheit die Ergebnisse über Methoden (all TRUE):

all.equal(S2C[1,],S1[1,]) 
all.equal(S2C[1,],S2R[1,]) 
all.equal(my_row_extract(S2R,1),S2R[1,]) 
all.equal(my_row_extract(S2R,17),S2R[17,]) 

Benchmark:

benchmark(S1[1,], S2C[1,], S2R[1,], my_row_extract(S2R,1), 
      columns=c("test","elapsed","relative")) 
##      test elapsed relative 
## 4 my_row_extract(S2R, 1) 0.015 1.154 
## 1    S1[1, ] 0.013 1.000 
## 2    S2C[1, ] 0.563 43.308 
## 3    S2R[1, ] 4.113 316.385 

Der Zweck Extraktor ist konkurrierend mit Basismatrices. S2R ist super-langsam, sogar für die Zeilenextraktion (überraschend); jedoch sagen ?"dgRMatrix-class" tut

Hinweis: Die Säule orientierte spärlich Klassen, zum Beispiel ‚dgCMatrix‘, sind bevorzugt und besser in der ‚Matrix‘ Paket unterstützt.

Verwandte Themen