2013-03-05 79 views
3

我想用apply來遍歷矩陣的行,我想在我的函數中使用當前行的rowname。看來你不能直接在函數中使用rownamescolnames,dimnamesnames。我知道我可以根據this question中的信息創建一個解決方法。R:rownames,colnames,dimnames和name

但我的問題是,apply如何在它的第一個參數中處理數組的行名和列名,以及如何將名稱賦值給由apply調用的函數內部創建的對象?這似乎有點不一致,我希望通過下面的例子來展示。是否有這樣設計的原因?

# Toy data 
m <- matrix(runif(9) , nrow = 3) 
rownames(m) <- LETTERS[1:3] 
colnames(m) <- letters[1:3] 
m 
      a   b   c 
A 0.5092062 0.3786139 0.120436569 
B 0.7563015 0.7127949 0.003358308 
C 0.8794197 0.3059068 0.985197273 

# These return NULL 
apply(m , 1 , FUN = function(x){ rownames(x) }) 
NULL 
apply(m , 1 , FUN = function(x){ colnames(x) }) 
NULL 
apply(m , 1 , FUN = function(x){ dimnames(x) }) 
NULL 

# But... 
apply(m , 1 , FUN = function(x){ names(x) }) 
    A B C 
[1,] "a" "a" "a" 
[2,] "b" "b" "b" 
[3,] "c" "c" "c" 
# This looks like a column-wise matrix of colnames, with the rownames of m as the column names to me 

# And further you can get... 
n <- apply(m , 1 , FUN = function(x){ names(x) }) 
dimnames(n) 
[[1]] 
NULL 

[[2]] 
[1] "A" "B" "C" 

# But you can't do... 
apply(m , 1 , FUN = function(x){ n <- names(x); dimnames(n) }) 
NULL 

我只是想了解在內部應用會發生什麼?非常感謝。

回答

7

我覺得你的困惑源於這樣一個事實,即apply沒有將一個數組(或矩陣)傳遞給FUN中指定的函數。

它依次通過矩陣的每一行。每行本身是「唯一」的一個(命名)向量:

> m[1,] 
     a   b   c 
0.48768161 0.61447934 0.08718875 

所以你的函數只有這個命名向量來處理。

對於你的中間例如,如記載於apply

如果每次調用FUN返回長度爲n的矢量,然後應用返回 尺寸c(N,暗淡(X)[MARGIN的陣列]),如果n> 1。如果n等於1,則 apply將返回一個向量,如果MARGIN長度爲1並且數組爲 dimension dim(X)[MARGIN]否則返回。

所以function(x) names(x)爲每一行返回一個長度爲3的向量,所以最終的結果就是你看到的矩陣。但是該矩陣在apply函數的結尾處構造,其中FUN的結果單獨應用於每行。