web-dev-qa-db-fra.com

Combinaison de matrices dans un tableau en R

Si j'ai créé plusieurs matrices, comment puis-je les combiner dans un tableau? J'ai 8 matrices qui ont chacune 200 lignes et 200 colonnes et je dois les combiner dans un tableau avec dim = 200,200,8. Je veux donc que chacune de mes matrices soit une tranche de mon tableau.

24
user2113499

voici l'exemple pour deux. vous pouvez facilement l'étendre à huit

# create two matricies with however many rows and columns
x <- matrix( 1:9 , 3 , 3 )
y <- matrix( 10:18 , 3 , 3 )
# look at your starting data
x
y

# store both inside an array, with the same first two dimensions,
# but now with a third dimension equal to the number of matricies
# that you are combining
z <- array( c( x , y ) , dim = c( 3 , 3 , 2 ) )

# result
z
18
Anthony Damico

Vous pouvez utiliser la fonction abind du package abind:

library(abind)
newarray <- abind( mat1, mat2, mat3, mat4, along=3 )

## or if mats are in a list (a good idea)

newarray <- abind( matlist, along=3 )
26
Greg Snow

Voici une version similaire à abind-, mais sans utiliser de paquet supplémentaire. Rassemblez tout dans une list et utilisez ensuite l'option sapply pour simplify= en "array", après n'avoir rien fait pour chaque partie de la liste (identity renvoie simplement l'objet et équivaut à function(x) x):

sapply(list(x,y), identity, simplify="array")
# similarly to save a couple of keystrokes, the following is usually identical
sapply(list(x,y), I, simplify="array")

#, , 1
#
#     [,1] [,2] [,3]
#[1,]    1    4    7
#[2,]    2    5    8
#[3,]    3    6    9
#
#, , 2
#
#     [,1] [,2] [,3]
#[1,]   10   13   16
#[2,]   11   14   17
#[3,]   12   15   18

Si vous souhaitez conserver les noms de chaque matrice d'origine dans votre nouveau tableau en tant qu'identificateurs, essayez:

sapply(mget(c("x","y")), identity, simplify="array")

Future me note également que cela équivaut à simplify2array:

simplify2array(list(x,y))
7
thelatemail

Cela dépend si vous voulez les combiner colonne-majeur ou ligne-majeur. Cela revient à utiliser cbind et rbind pour combiner des vecteurs dans une matrice. Parce que R stocke les matrices dans l'ordre des colonnes, c'est le plus facile à accomplir:

matrices <- list(
  matrix( 1:9 , 3 , 3 ),
  matrix( 10:18 , 3 , 3 )
);

#it is assumed all matrices in the list have equal dimensions
array1 <- array(
  data = do.call(cbind, matrices), 
  dim = c(dim(matrices[[1]]), length(matrices))
);

La nouvelle dimension (2 dans ce cas) deviendra la 3ème dimension. À en juger par le résultat de la méthode d’impression, cela semble précis, car il scinde l’impression par la dernière dimension:

> print(array1)
, , 1

     [,1] [,2] [,3]
[1,]    1    4    7
[2,]    2    5    8
[3,]    3    6    9

, , 2

     [,1] [,2] [,3]
[1,]   10   13   16
[2,]   11   14   17
[3,]   12   15   18

Cependant, vous aurez parfois besoin de les combiner avec la première dimension, par exemple:

array2 <- array (
  data = do.call(rbind, lapply(matrices, as.vector)), 
  dim = c(length(matrices), dim(matrices[[1]]))
);

print(array2[1,,])

     [,1] [,2] [,3]
[1,]    1    4    7
[2,]    2    5    8
[3,]    3    6    9 

Par exemple, supposons que vous souhaitiez affecter ces matrices à un bloc de données avec colonne; une matrice pour chaque ligne. Ensuite, les premières dimensions, a.k.a nrow doivent correspondre dans le tableau et le cadre de données:

 mydf <- data.frame(foo = 1:2, row.names=c("first", "second"))
 mydf$bar <- array1
  Error in `$<-.data.frame`(`*tmp*`, "bar", value = 1:18) : 
    replacement has 3 rows, data has 2

 mydf$bar <- array2
 mydf$bar
2
Jeroen

Connexes: Comment empiler plusieurs matrices dans R

Le problème avec toutes les solutions à ce jour est que lorsque les matrices (et non pas data.frames - pour cette dplyr et data.table fonctionnent correctement) n'ont pas le même ordre de lignes et de colonnes, bind empilera des valeurs qui ne sont pas liées.

Si vous voulez vérifier et prendre en compte les noms dans chaque dimension, regardez narray :

 enter image description here

(disclaimer: j'ai écrit le paquet)

0
Michael Schubert
library('abind')
abind(m1, m2, m3, along = 2.5)
abind(m1, m2, m3, along = 3)

m4 <- list(m1, m2, m3)
abind(m4, along = 3) 

       along        input = matrix + matrix                       output 
----------------------------------------------------------------------------
        0         split columns and row bind them                 array
        0.5       same as 0                                       array
        1         combine matrices into one matrix by rowwise     matrix
        1.5       split columns and column bind them              array
        2         combine matrices into one matrix by columnwise  matrix
        2.5       Form an array with matrices                     array
        3         Same as 2.5                                     array
0
Sathish

Que dis-tu de ça:

combmat <- array(dim=c(200,200,8), data=cbind(matrix1,matrix2,...,matrix8) )
0
nadizan