2015-12-10 42 views
2

我有一個表是這樣的:重塑相關矩陣,包括每對變量只有一次

A B C D E 
7 1 6 8 7 
9 3 9 5 9 
4 6 2 1 10 
10 5 3 4 1 
1 3 5 9 3 
6 4 8 7 6 

我與表中的每一其它變量尋找每個變量的相關性的過程。這是R代碼我使用:

test <- read.csv("D:/AB/test.csv") 
iterations <- ncol(test) 
correlation <- matrix(ncol = 3 , nrow = iterations * iterations) 
for (k in 1:iterations) { 
    for (l in 1:iterations){ 
    corr <- cor(test[,k], test[,l]) 
    corr_string_A <- names(test[k]) 
    corr_string_B <- names(test[l]) 
    correlation[l + ((k-1) * iterations),] <- rbind(corr_string_A, corr_string_B, corr)   
    } 
} 

以下是我接收到的輸出:

Var1 Var2  value 
1  A A 1.00000000 
2  B A 0.50018605 
3  C A -0.35747393 
4  D A -0.25670054 
5  E A -0.02974821 
6  A B 0.50018605 
7  B B 1.00000000 
8  C B 0.56070716 
9  D B 0.46164928 
10 E B 0.16813991 
11 A C -0.35747393 
12 B C 0.56070716 
13 C C 1.00000000 
14 D C 0.52094589 
15 E C 0.23190036 
16 A D -0.25670054 
17 B D 0.46164928 
18 C D 0.52094589 
19 D D 1.00000000 
20 E D -0.39223227 
21 A E -0.02974821 
22 B E 0.16813991 
23 C E 0.23190036 
24 D E -0.39223227 
25 E E 1.00000000 

然而,我不想從上部三角的值;即不應該出現對角線值,並且每個獨特的組合應該只出現一次。最終的輸出應該是這樣的:

Var1 Var2  value 
1  B A 0.50018605 
2  C A -0.35747393 
3  D A -0.25670054 
4  E A -0.02974821 
5  C B 0.56070716 
6  D B 0.46164928 
7  E B 0.16813991 
8  D C 0.52094589 
9  E C 0.23190036 
10 E D -0.39223227 

據我所知,有使用它像重塑了幾個技術可以實現上面的輸出,但我想使上述R代碼,以滿足生產上述結果。

我相信第二個for循環中的「n」應該被動態改變,這可以幫助實現這一點。但是我不確定如何使這項工作。

+3

你就不能這樣做'心病(測試)'。從你的輸出中,我想,'相關性[(相關性,Var1!= Var2),]' – akrun

+3

'?cor'的第二個例子... – Henrik

+0

@akrun - 謝謝。但由於某些特定的工作目的,上述R代碼將適合我而不是cor(測試)或重塑功能等。 – Arun

回答

4

You can轉換您相關矩陣與3列格式與as.data.frameas.table,然後限制值上方或下方的對角線可以與subset來完成。

subset(as.data.frame(as.table(cor(dat))), 
     match(Var1, names(dat)) > match(Var2, names(dat))) 
# Var1 Var2  Freq 
# 2  B A -0.02299154 
# 3  C A 0.23155350 
# 4  D A -0.28036851 
# 5  E A -0.05230260 
# 8  C B -0.58384036 
# 9  D B -0.80175393 
# 10 E B 0.00000000 
# 14 D C 0.52094589 
# 15 E C 0.23190036 
# 20 E D -0.39223227 

注意,對於更大的數據集,這應該是遠遠超過對變量對因cor被矢量分別調用cor更高效,並進一步將其顯然打字少了很多。

如果你真的必須保持循環的代碼,那麼你可以用小的改動對for循環和有關的correlation行一些簿記達到您想要的結果,你是計算:

iterations <- ncol(test) 
correlation <- matrix(ncol = 3 , nrow = choose(iterations, 2)) 
pos <- 1 
for (k in 2:iterations) { 
    for (l in 1:(k-1)){ 
    corr <- cor(test[,k], test[,l]) 
    corr_string_A <- names(test[k]) 
    corr_string_B <- names(test[l]) 
    correlation[pos,] <- rbind(corr_string_A, corr_string_B, corr)   
    pos <- pos+1 
    } 
} 

不過,我真的不會建議這種循環解決方案;最好是使用我提供的單行數據,然後處理所有生成的值NA

2

從OP的環路輸出,我們可以子集行,

df1[!duplicated(t(apply(df1[1:2], 1, sort))) & df1[,1]!=df1[,2],] 
# Var1 Var2  value 
#2  B A 0.50018605 
#3  C A -0.35747393 
#4  D A -0.25670054 
#5  E A -0.02974821 
#8  C B 0.56070716 
#9  D B 0.46164928 
#10 E B 0.16813991 
#14 D C 0.52094589 
#15 E C 0.23190036 
#20 E D -0.39223227 

或者像我在評論中提到的(第一個),只需使用

cor(test)