pack() coerces dense symmetric and dense triangular matrices from unpacked format (storing the full matrix) to packed format (storing only one of the upper and lower triangles). unpack() performs the reverse coercion. The two formats are formalized by the virtual classes "packedMatrix" and "unpackedMatrix".

pack(x, ...)
# S4 method for class 'dgeMatrix'
pack(x, symmetric = NA, upperTri = NA, ...)
# S4 method for class 'lgeMatrix'
pack(x, symmetric = NA, upperTri = NA, ...)
# S4 method for class 'ngeMatrix'
pack(x, symmetric = NA, upperTri = NA, ...)
# S4 method for class 'matrix'
pack(x, symmetric = NA, upperTri = NA, ...)

unpack(x, ...)

Arguments

x

A dense symmetric or dense triangular matrix.

For pack():

typically an "unpackedMatrix" or a standard "matrix", though "packedMatrix" are allowed and returned unchanged.

For unpack():

typically a "packedMatrix", though "unpackedMatrix" are allowed and returned unchanged.

symmetric

logical (including NA) optionally indicating whether x is symmetric (or triangular).

upperTri

(for triangular x only) logical (including NA) indicating whether x is upper (or lower) triangular.

...

further arguments passed to or from other methods.

Value

For pack():

a "packedMatrix" giving the condensed representation of x.

For unpack():

an "unpackedMatrix" giving the full storage representation of x.

Details

pack(x) checks matrices x not inheriting from one of the virtual classes "symmetricMatrix" "triangularMatrix" for symmetry (via isSymmetric()) then for upper and lower triangularity (via isTriangular()) in order to identify a suitable coercion. Setting one or both of symmetric and upperTri to TRUE or FALSE rather than NA allows skipping of irrelevant tests for large matrices known to be symmetric or (upper or lower) triangular.

Users should not assume that pack() and unpack() are inverse operations. Specifically, y <- unpack(pack(x)) may not reproduce an "unpackedMatrix" x in the sense of identical(). See the examples.

Examples

showMethods("pack")
#> Function: pack (package Matrix)
#> x="dgeMatrix"
#> x="dpoMatrix"
#>     (inherited from: x="unpackedMatrix")
#> x="dsyMatrix"
#>     (inherited from: x="unpackedMatrix")
#> x="dtrMatrix"
#>     (inherited from: x="unpackedMatrix")
#> x="lgeMatrix"
#> x="ltrMatrix"
#>     (inherited from: x="unpackedMatrix")
#> x="matrix"
#> x="ngeMatrix"
#> x="ntrMatrix"
#>     (inherited from: x="unpackedMatrix")
#> x="packedMatrix"
#> x="unpackedMatrix"
#> 
(s <- crossprod(matrix(sample(15), 5,3))) # traditional symmetric matrix
#>      [,1] [,2] [,3]
#> [1,]  434  303  409
#> [2,]  303  311  230
#> [3,]  409  230  495
(sp <- pack(s))
#> 3 x 3 Matrix of class "dspMatrix"
#>      [,1] [,2] [,3]
#> [1,]  434  303  409
#> [2,]  303  311  230
#> [3,]  409  230  495
mt <- as.matrix(tt <- tril(s))
(pt <- pack(mt))
#> 3 x 3 Matrix of class "dtpMatrix"
#>      [,1] [,2] [,3]
#> [1,]  434    .    .
#> [2,]  303  311    .
#> [3,]  409  230  495
stopifnot(identical(pt, pack(tt)),
    dim(s ) == dim(sp), all(s  == sp),
    dim(mt) == dim(pt), all(mt == pt), all(mt == tt))

showMethods("unpack")
#> Function: unpack (package Matrix)
#> x="matrix"
#> x="packedMatrix"
#> x="unpackedMatrix"
#> 
(cp4 <- chol(Hilbert(4))) # is triangular
#> 4 x 4 Matrix of class "dtrMatrix"
#>      [,1]       [,2]       [,3]       [,4]      
#> [1,] 1.00000000 0.50000000 0.33333333 0.25000000
#> [2,]          . 0.28867513 0.28867513 0.25980762
#> [3,]          .          . 0.07453560 0.11180340
#> [4,]          .          .          . 0.01889822
tp4 <- pack(cp4) # [t]riangular [p]acked
str(tp4)
#> Formal class 'dtpMatrix' [package "Matrix"] with 5 slots
#>   ..@ uplo    : chr "U"
#>   ..@ Dim     : int [1:2] 4 4
#>   ..@ Dimnames:List of 2
#>   .. ..$ : NULL
#>   .. ..$ : NULL
#>   ..@ x       : num [1:10] 1 0.5 0.289 0.333 0.289 ...
#>   ..@ diag    : chr "N"
(unpack(tp4))
#> 4 x 4 Matrix of class "dtrMatrix"
#>      [,1]       [,2]       [,3]       [,4]      
#> [1,] 1.00000000 0.50000000 0.33333333 0.25000000
#> [2,]          . 0.28867513 0.28867513 0.25980762
#> [3,]          .          . 0.07453560 0.11180340
#> [4,]          .          .          . 0.01889822
stopifnot(identical(tp4, pack(unpack(tp4))))

z1 <- new("dsyMatrix", Dim = c(2L, 2L), x = as.double(1:4), uplo = "U")
z2 <- unpack(pack(z1))
stopifnot(!identical(z1, z2), # _not_ identical
          all(z1 == z2)) # but mathematically equal
cbind(z1@x, z2@x) # (unused!) lower triangle is "lost" in translation
#>      [,1] [,2]
#> [1,]    1    1
#> [2,]    2    0
#> [3,]    3    3
#> [4,]    4    4