在多种条件下删除矩阵行

时间:2019-08-06 02:35:51

标签: r for-loop if-statement conditional-statements subset

最好通过示例解决此问题。

设置

Mat1 <- matrix(nrow =9, ncol =11)
colnames(Mat1) <- c("Name", "Strategy.Assets", "Jan.94", "Jan.95", "Jan.96", "Jan.97", "1", "2", "3","4", "5")
Mat1[,1] <- letters[1:9]
Mat1[,2] <- cbind(20,30,40,50,60,30,30,40,50)
Mat1[,3:6] <- rnorm(36,0,1)
Mat1[,7] <- c(0,0,0,0,0,0,0,0,0)
Mat1[,8] <- c(0.95, 0.8, 0,0,0,0,0,0,0)
Mat1[,9] <- c(0.95,0.6,0.7,0,0,0,0,0,0)
Mat1[,10] <- c(0.08, 0.09, 0.99, 0.93, 0,0,0,0,0)
Mat1[,11] <- c(0.09,0.01,0.04,0.97, 0.80,0,0,0,0)

data.frame(Mat1)

处理列“ 1”,“ 2”,“ 3”,“ 4”,“ 5”,“ 6”作为相关矩阵的开始(应该是9 x 9,但我只显示前6列)。

对于第1至6列中的每一行,我需要确定是否存在> = 0.95的值。如果有,我需要知道这个位置。在这种情况下,值0.95出现在相关矩阵的m = 1,n = 2中。然后,我需要转到“战略资产”列,并比较第1行和第2行(在本例中为20和30)中的值。此后,我需要省略具有较低值的行(因为20小于30,所以第1行)。删除一行后,我需要进入相关矩阵的下一行-我们看到在第2行中,没有任何值至少等于0.95。然后,我们进入第三行。然后我们看到在位置m = 3,n = 4处出现0.99> 0.95。然后,我们转到“战略资产”,比较第3行和第4行中的值。在第3行中,策略资产= 40,第4行= 50。因此,我们省略了第3行。然后,我们进行到相关矩阵的第4行。在位置4,5出现0.99。然后,我们需要比较策略资产中的第4行和第5行。我们看到第5行= 60,第4 = 50行,因此需要省略第4行。

我需要对相关矩阵中的所有行重复此过程。

请注意,相关矩阵的项(1,3)也等于0.95。但是,由于row1已被删除(从第一次迭代中删除),因此在这种情况下,我不需要循环继续运行。

  > data.frame(Mat1)
  Name Strategy.Assets             Jan.94             Jan.95             Jan.96              Jan.97 X1   X2   X3   X4   X5
1    a              20   2.95438832384095  0.322838398649362  0.265489849080971   -1.26762589628627  0 0.95 0.95 0.08 0.09
2    b              30 -0.231467724347497   1.36209337396348  0.244352997300369   0.147019042483708  0  0.8  0.6 0.09 0.01
3    c              40 -0.725388339795491 0.0813983643917171  -0.50418751522557   0.802967414744253  0    0  0.7 0.99 0.04
4    d              50 -0.120645568994363    1.7770242881308 -0.798437656907533    1.03842921924565  0    0    0 0.93 0.97
5    e              60  0.818447801042692 -0.767858384307916  -1.23187047713004 -0.0779863946287645  0    0    0    0  0.8
6    f              30 -0.231572883434978  0.266559660007751  0.720829574412722 -0.0207732265889516  0    0    0    0    0
7    g              30  0.444651868913969  0.832322051653509 -0.538333881677844   0.291130047037627  0    0    0    0    0
8    h              40   2.00827324376109  0.775006479679076 0.0323592399331455   -2.33121256833447  0    0    0    0    0
9    i              50 -0.368493048065977   1.30727697822673 -0.446402751994181 -0.0616057412430855  0    0    0    0    0

然后我想要的输出是:

output <- data.frame(rbind(Mat1[2,1:6], Mat1[5:9,1:6]))
output

  Name Strategy.Assets             Jan.94             Jan.95             Jan.96              Jan.97
1    b              30 -0.231467724347497   1.36209337396348  0.244352997300369   0.147019042483708
2    e              60  0.818447801042692 -0.767858384307916  -1.23187047713004 -0.0779863946287645
3    f              30 -0.231572883434978  0.266559660007751  0.720829574412722 -0.0207732265889516
4    g              30  0.444651868913969  0.832322051653509 -0.538333881677844   0.291130047037627
5    h              40   2.00827324376109  0.775006479679076 0.0323592399331455   -2.33121256833447
6    i              50 -0.368493048065977   1.30727697822673 -0.446402751994181 -0.0616057412430855

我需要能够将此功能应用于列表中的矩阵。列表中的每个矩阵具有不同的行数,因此具有不同的列数。但是,前6列始终相同。本质上,'names'变量增加(可能是从a到z),导致相关矩阵增加(在这种情况下将是26乘26)。

1 个答案:

答案 0 :(得分:2)

如果我对您的理解正确,一种方法可能是使用which首先找出相关列的值大于等于0.95的行和列索引。对于每对行和列,我们找出相应的最小值,并将其从原始Mat1中删除。

mat <- which(Mat1[, as.character(1:5)] >= 0.95, arr.ind = TRUE)
Mat1[-unique(apply(mat, 1, function(x) x[which.min(Mat1$Strategy.Assets[x])])), ]


#  Name Strategy.Assets      Jan.94      Jan.95     Jan.96     Jan.97 1   2   3    4    5
#2    b              30 -0.02101158  1.27504998 -0.9534582 -0.6917499 0 0.8 0.6 0.09 0.01
#5    e              60 -0.88500700 -1.19165574 -1.6309657  0.6183648 0 0.0 0.0 0.00 0.80
#6    f              30 -0.45072999 -0.04698659  0.7462178  0.5858741 0 0.0 0.0 0.00 0.00
#7    g              30  1.29131284 -1.60004027 -0.9681269  0.9595044 0 0.0 0.0 0.00 0.00
#8    h              40  0.37883959 -1.11536574 -0.3041997 -0.8202406 0 0.0 0.0 0.00 0.00
#9    i              50  1.50068308  0.89465888  0.6646096  0.4433313 0 0.0 0.0 0.00 0.00

数据

Mat1 <- data.frame(matrix(nrow =9, ncol =11))
colnames(Mat1) <- c("Name", "Strategy.Assets", "Jan.94", "Jan.95", "Jan.96", 
                 "Jan.97", "1", "2", "3","4", "5")

Mat1[,1] <- letters[1:9]
Mat1[,2] <- c(20,30,40,50,60,30,30,40,50)
Mat1[,3:6] <- rnorm(36,0,1)
Mat1[,7] <- c(0,0,0,0,0,0,0,0,0)
Mat1[,8] <- c(0.95, 0.8, 0,0,0,0,0,0,0)
Mat1[,9] <- c(0.95,0.6,0.7,0,0,0,0,0,0)
Mat1[,10] <- c(0.08, 0.09, 0.99, 0.93, 0,0,0,0,0)
Mat1[,11] <- c(0.09,0.01,0.04,0.97, 0.80,0,0,0,0)