了解R中列与行索引的语法

时间:2014-05-08 04:50:23

标签: r indexing row multiple-columns

我对R数据帧的过滤方案感到有点困惑。

例如,我们假设我们有以下标题为dframe的数据框:

> str(dframe)
'data.frame':   143 obs. of  3 variables:
 $ Year     : int  1999 2005 2007 2008 2009 2010 2005 2006 2007 2008 ...
 $ Name     : Factor w/ 18 levels "AADAM","AADEN",..: 1 1 2 2 2 2 3 3 3 3 ...
 $ Frequency: int  5 6 10 34 38 12 10 6 10 5 ...

现在,如果我想过滤名称的值为" AADAM"的dframe,则正确的过滤器是: dframe[dframe$Name=="AADAM",]

我感到困惑的部分是为什么逗号并不是第一位的。为什么不是这样的:dframe[,dframe$Name=="AARUSH"]

4 个答案:

答案 0 :(得分:3)

您必须记住,当您进行子设置时,逗号之前的部分指定了您想要的行,而逗号之后的部分指定了您想要的列。即:

dframe[rowsyouwant, columnsyouwant]

您根据列进行过滤,但是您希望结果中包含所有列,因此逗号后的空格为空。您需要一些行的子集,因此您的过滤规范将在逗号之前,指定所需的行。

答案 1 :(得分:3)

更新:您澄清了您的问题实际上是“请举例说明哪种逻辑表达式对过滤列有效?”

我同意你的语法最初看起来很奇怪,但它有以下逻辑。

最重要的是,列过滤器表达式通常不如行过滤表达式丰富和富有表现力,特别是您不能像对待行一样对逻辑索引进行链接。

最好的方法是将索引表达式视为一般形式:

dframe[<row-index-expression>,<col-index-expression>]

其中 index-expression是可选的,所以你可以做一个,我们(至关重要!)需要逗号来消除歧义,无论是行索引还是列索引:

dframe[<row-index-expression>,] # such as dframe[dframe$Name=="ADAM",]

dframe[,<col-index-expression>]

在我们查看col-index-expression的示例以及包含在其中的有效(和无效)的示例之前,让我们回顾一下R讨论R的编制方式 - 当我开始使用它时,我有同样的困惑。

在此示例中,您有三列。您可以通过字符串名称 '年','名称','频率' 来引用它们。您还可以通过列索引 1,2,3 来引用它们,其中数字1,2,3对应于条目colnames(dframe)。 R使用'['运算符进行索引,也使用'[['运算符)。以下是索引列索引的方法的一些有效示例:

dframe[,2]       # column 2 / Name
dframe[,'Name']  # column 2 / Name
dframe[,c('Name','Frequency')]  # string vector - very common
dframe[,c(2,3)]                 # integer vector - also very common
dframe[,c(F,T,T)]               # logical vector - very rarely seen, and a pain in the butt to compute

现在,如果您选择对列索引使用逻辑表达式,则它必须是不使用列名的有效表达式 - 在列中它不知道自己的名称。 假设你想动态过滤“只给我dframe中的因子列”。 类似的东西:

unlist(apply(dframe[1,1:3], 2, is.factor), use.names=F) # except I can't seem to remove the colnames

有关索引的更多帮助和示例,请查看'['运算符帮助页面: 输入?'['

dframe[,dframe$Name=="ADAM"]对列索引的尝试无效,因为列无法识别名称==“ADAM”

附录:生成示例数据帧的代码(因为您没有向我们转储dput输出)

set.seed(123)
N = 10
randomName <- function() { cat(sample(letters, size=runif(1)*6+2, replace=T), sep='') }    
dframe = data.frame(Year=round(runif(N,1980,2014)),
                    Name = as.factor(replicate(N, randomName())),
                    Frequency=round(runif(N, 2,40)))

答案 2 :(得分:1)

正如其他人所说,括号内的结构是row,然后是column

我想到了使用以下方法从data.frame中选择数据的语法的一种方法:

dframe[dframe$Name=="AADAM",]

是想到一个名词,然后是一个动词,其中:

dframe[]是名词。它是您要执行操作的对象

[dframe$Name=="AADAM",]是动词。这是您想要执行的操作。

我有一种愚蠢的方式向自己表达这一点,但它让我记住了事情:

嘿,你! dframe!我将......在这种情况下,选择rows等于Name的所有AADAM

[dframe$Name=="AADAM",]的列部分保留为空,表示您要保留所有列。

有时可能有点难以记住你必须在括号内外写dframe

至于为什么row排在第一位,column排在第二位,我不知道,但row必须是第一位或第二位。

dframe <- read.table(text = '
     Year Name Frequency
       1  ADAM     4
       3  BOB     10
       7  SALLY    5
       2  ADAM    12
       4  JIM      3
      12  ADAM     7
', header = TRUE)

dframe[,dframe$Name=="ADAM"]

# Error in `[.data.frame`(dframe, , dframe$Name == "ADAM") : 
#   undefined columns selected

dframe[dframe$Name=="ADAM",]

#   Year Name Frequency
# 1    1 ADAM         4
# 4    2 ADAM        12
# 6   12 ADAM         7

dframe[,'Name']

# [1] ADAM  BOB   SALLY ADAM  JIM   ADAM 
# Levels: ADAM BOB JIM SALLY


dframe[dframe$Name=="ADAM",'Name']

# [1] ADAM ADAM ADAM
# Levels: ADAM BOB JIM SALLY

答案 3 :(得分:1)

正如其他人所指出的那样,请求数据帧的某个子集需要语法[rows, columns]。自dframe[has 143 rows, has 3 columns]起,对dframe某些部分的任何请求都应采用

形式
dframe[which of the 143 rows do I want?, which of the 3 columns do I want?].

由于dframe$Name是长度为143的向量,因此比较dframe$Name=='AADAM'是T / F值的向量,其长度也为143.因此,

dframe[dframe$Name=='AADAM',]

就像说

dframe[of the 143 rows I want these ones, I want all columns]

,而

dframe[,dframe$Name=='AADAM']

生成错误,因为它就像是在说

dframe[I want all rows, of the 143 columns I want these ones]

另外,如果您还不熟悉subset()功能,可能需要查看subset(dframe, Name=='AADAM')功能。您可以通过编写{{1}}

来获得相同的结果