简体   繁体   English

在 R 中将矩阵按行划分为子矩阵列表

[英]Partition a matrix into list of sub matrices row-wise in R

I have a matrix where each row is either all 1's or any number between 0 and 1. I need to partition this into list of matrices such that我有一个矩阵,其中每一行都是 1 或 0 到 1 之间的任何数字。我需要将其划分为矩阵列表,以便

  1. Each sub matrix is either all 1's or all numbers between 0 and 1每个子矩阵要么全为 1,要么全为 0 到 1 之间的数字
  2. Combining all the sub matrices of the list using rbind yields the original matrix使用rbind组合列表的所有子矩阵产生原始矩阵

Example:例子:

样本矩阵

子矩阵列表

m <- 
structure(c(1, 1, 1, 0.84, 0.27, 0.24, 0.48, 0.28, 0.62, 0.55, 
1, 1, 0.26, 0.93, 0.87, 0.76, 1, 1, 1, 1, 1, 0.31, 0.32, 0.96, 
0.25, 0.96, 0.43, 0.66, 1, 1, 0.22, 0.88, 0.01, 0.14, 1, 1, 1, 
1, 1, 0.71, 0.99, 0.6, 0.22, 0.73, 0.54, 0.17, 1, 1, 0.59, 0.67, 
0.07, 0.4, 1, 1, 1, 1, 1, 0.27, 0.62, 0.52, 0.67, 0.69, 0.06, 
0.63, 1, 1, 0.27, 0.95, 0.16, 0.22, 1, 1, 1, 1, 1, 0.59, 0.94, 
0.4, 0.05, 0.05, 0.26, 0.31, 1, 1, 0.53, 0.52, 0.77, 0.06, 1, 
1, 1, 1, 1, 0.48, 0.47, 0.88, 0.7, 0.4, 0.4, 0.72, 1, 1, 0.79, 
0.58, 0.74, 0.4, 1, 1, 1, 1, 1, 0.27, 0.41, 0.36, 0.35, 0.48, 
0.2, 0.4, 1, 1, 0.17, 0.34, 0.97, 0.06, 1, 1, 1, 1, 1, 0.56, 
0.66, 0.29, 0.41, 0.56, 0.83, 0.97, 1, 1, 0.4, 0.35, 0.47, 0.23, 
1, 1, 1, 1, 1, 0.91, 0.15, 0.17, 0.82, 0.7, 0.15, 0.97, 1, 1, 
0.47, 0.02, 0.07, 0.05, 1, 1, 1, 1, 1, 0.9, 0.57, 0.17, 0.92, 
0.92, 0.8, 0.73, 1, 1, 0.87, 0.5, 0.65, 0.67, 1, 1), .Dim = c(18L, 
10L))

L <- 
list(structure(c(1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1), .Dim = c(3L, 10L
)), structure(c(0.84, 0.27, 0.24, 0.48, 0.28, 0.62, 0.55, 0.31, 
0.32, 0.96, 0.25, 0.96, 0.43, 0.66, 0.71, 0.99, 0.6, 0.22, 0.73, 
0.54, 0.17, 0.27, 0.62, 0.52, 0.67, 0.69, 0.06, 0.63, 0.59, 0.94, 
0.4, 0.05, 0.05, 0.26, 0.31, 0.48, 0.47, 0.88, 0.7, 0.4, 0.4, 
0.72, 0.27, 0.41, 0.36, 0.35, 0.48, 0.2, 0.4, 0.56, 0.66, 0.29, 
0.41, 0.56, 0.83, 0.97, 0.91, 0.15, 0.17, 0.82, 0.7, 0.15, 0.97, 
0.9, 0.57, 0.17, 0.92, 0.92, 0.8, 0.73), .Dim = c(7L, 10L)), 
    structure(c(1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1), .Dim = c(2L, 10L)), structure(c(0.26, 0.93, 
    0.87, 0.76, 0.22, 0.88, 0.01, 0.14, 0.59, 0.67, 0.07, 0.4, 
    0.27, 0.95, 0.16, 0.22, 0.53, 0.52, 0.77, 0.06, 0.79, 0.58, 
    0.74, 0.4, 0.17, 0.34, 0.97, 0.06, 0.4, 0.35, 0.47, 0.23, 
    0.47, 0.02, 0.07, 0.05, 0.87, 0.5, 0.65, 0.67), .Dim = c(4L, 
    10L)), structure(c(1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 
    1, 1, 1, 1, 1, 1, 1), .Dim = c(2L, 10L)))

Here is a solution for you. 这是为您提供的解决方案。 It uses data.table's rleid for convenience. 为了方便起见,它使用data.table的rleid。

First, we generate some data: 首先,我们生成一些数据:

set.seed(123)
input <- matrix(runif(180),ncol=10)
input[c(1:3,5,9:10),]<-1

Then we identify which rows have only ones 然后我们确定哪些行只有一个

is_one <- apply(input,1,function(x){all(x==1)})

We want to split our rows by groups of is one/is not one, so we generate row id's and split id's 我们想将行按1 /不是1的组进行拆分,因此我们生成行ID和拆分ID

row_ids <- 1:nrow(input)
split_ids <- data.table::rleid(is_one)

The we generate our output, by splitting the row id's by groups of is one/is not one and returning our input data for each set of row ids. 我们通过将行ID分为1个/非1个组,并返回每组行ID的输入数据,来生成输出。

output <- lapply(split(row_ids,split_ids),function(x){input[x,]})

You can also use split.data.frame with a matrix:您还可以将split.data.frame与矩阵一起使用:

> m=structure(c(1,1,1,0.84,0.27,0.24,0.48,0.28,0.62,0.55,1,1,0.26,0.93,0.87,0.76,1,1,1,1,1,0.31,0.32,0.96,0.25,0.96,0.43,0.66,1,1,0.22,0.88,0.01,0.14,1,1,1,1,1,0.71,0.99,0.6,0.22,0.73,0.54,0.17,1,1,0.59,0.67,0.07,0.4,1,1,1,1,1,0.27,0.62,0.52,0.67,0.69,0.06,0.63,1,1,0.27,0.95,0.16,0.22,1,1,1,1,1,0.59,0.94,0.4,0.05,0.05,0.26,0.31,1,1,0.53,0.52,0.77,0.06,1,1,1,1,1,0.48,0.47,0.88,0.7,0.4,0.4,0.72,1,1,0.79,0.58,0.74,0.4,1,1,1,1,1,0.27,0.41,0.36,0.35,0.48,0.2,0.4,1,1,0.17,0.34,0.97,0.06,1,1,1,1,1,0.56,0.66,0.29,0.41,0.56,0.83,0.97,1,1,0.4,0.35,0.47,0.23,1,1,1,1,1,0.91,0.15,0.17,0.82,0.7,0.15,0.97,1,1,0.47,0.02,0.07,0.05,1,1,1,1,1,0.9,0.57,0.17,0.92,0.92,0.8,0.73,1,1,0.87,0.5,0.65,0.67,1,1),.Dim=c(18L,10L))
> r=rle(rowSums(m==1)==ncol(m))$lengths
> split.data.frame(m,rep(1:length(r),r))
$`1`
     [,1] [,2] [,3] [,4] [,5] [,6] [,7] [,8] [,9] [,10]
[1,]    1    1    1    1    1    1    1    1    1     1
[2,]    1    1    1    1    1    1    1    1    1     1
[3,]    1    1    1    1    1    1    1    1    1     1

$`2`
     [,1] [,2] [,3] [,4] [,5] [,6] [,7] [,8] [,9] [,10]
[1,] 0.84 0.31 0.71 0.27 0.59 0.48 0.27 0.56 0.91  0.90
[2,] 0.27 0.32 0.99 0.62 0.94 0.47 0.41 0.66 0.15  0.57
[3,] 0.24 0.96 0.60 0.52 0.40 0.88 0.36 0.29 0.17  0.17
[4,] 0.48 0.25 0.22 0.67 0.05 0.70 0.35 0.41 0.82  0.92
[5,] 0.28 0.96 0.73 0.69 0.05 0.40 0.48 0.56 0.70  0.92
[6,] 0.62 0.43 0.54 0.06 0.26 0.40 0.20 0.83 0.15  0.80
[7,] 0.55 0.66 0.17 0.63 0.31 0.72 0.40 0.97 0.97  0.73

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

$`4`
     [,1] [,2] [,3] [,4] [,5] [,6] [,7] [,8] [,9] [,10]
[1,] 0.26 0.22 0.59 0.27 0.53 0.79 0.17 0.40 0.47  0.87
[2,] 0.93 0.88 0.67 0.95 0.52 0.58 0.34 0.35 0.02  0.50
[3,] 0.87 0.01 0.07 0.16 0.77 0.74 0.97 0.47 0.07  0.65
[4,] 0.76 0.14 0.40 0.22 0.06 0.40 0.06 0.23 0.05  0.67

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

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM