按逻辑条件过滤data.frame行

时间:2009-11-06 09:58:59

标签: r subset dataframe

我想根据逻辑条件从data.frame过滤行。我们假设我有像

这样的数据框
   expr_value     cell_type
1    5.345618 bj fibroblast
2    5.195871 bj fibroblast
3    5.247274 bj fibroblast
4    5.929771          hesc
5    5.873096          hesc
6    5.665857          hesc
7    6.791656          hips
8    7.133673          hips
9    7.574058          hips
10   7.208041          hips
11   7.402100          hips
12   7.167792          hips
13   7.156971          hips
14   7.197543          hips
15   7.035404          hips
16   7.269474          hips
17   6.715059          hips
18   7.434339          hips
19   6.997586          hips
20   7.619770          hips
21   7.490749          hips

我想要的是获得一个看起来相同但只有一个cell_type数据的新数据框。例如。子集/选择包含单元格类型“hesc”的行:

   expr_value     cell_type
1    5.929771          hesc
2    5.873096          hesc
3    5.665857          hesc

或者细胞类型“bj fibroblast”或“hesc”:

   expr_value     cell_type
1    5.345618 bj fibroblast
2    5.195871 bj fibroblast
3    5.247274 bj fibroblast
4    5.929771          hesc
5    5.873096          hesc
6    5.665857          hesc

有没有简单的方法可以做到这一点?

我试过了:

expr[expr[2] == 'hesc']
# [1] "5.929771" "5.873096" "5.665857" "hesc"     "hesc"     "hesc"    

如果原始数据框被称为“expr”,但它会以错误的格式显示结果,如您所见。

9 个答案:

答案 0 :(得分:181)

要根据 one 'cell_type'(例如'hesc')选择行,请使用==

expr[expr$cell_type == "hesc", ]

要根据两个或多个不同的'cell_type'选择行(例如'hesc''bj fibroblast'),请使用%in%

expr[expr$cell_type %in% c("hesc", "bj fibroblast"), ]

答案 1 :(得分:77)

使用subset(交互式使用)

subset(expr, cell_type == "hesc")
subset(expr, cell_type %in% c("bj fibroblast", "hesc"))

或更好dplyr::filter()

filter(expr, cell_type %in% c("bj fibroblast", "hesc"))

答案 2 :(得分:29)

expr[expr[2] == 'hesc']不起作用的原因是对于数据框,x[y]选择列而不是行。如果要选择行,请改为使用语法x[y,]

> expr[expr[2] == 'hesc',]
  expr_value cell_type
4   5.929771      hesc
5   5.873096      hesc
6   5.665857      hesc

答案 3 :(得分:20)

您可以使用dplyr包:

library(dplyr)
filter(expr, cell_type == "hesc")
filter(expr, cell_type == "hesc" | cell_type == "bj fibroblast")

答案 4 :(得分:2)

有时,您要过滤的列可能显示在与列索引2不同的位置,或者具有变量名称。

在这种情况下,您只需将要筛选的列名称引用为:

columnNameToFilter = "cell_type"
expr[expr[[columnNameToFilter]] == "hesc", ]

答案 5 :(得分:2)

我正在处理一个数据框,但运气不好,它总是返回0行,所以我找到并使用了grepl:

df = df[grepl("downlink",df$Transmit.direction),]

这基本上将我的数据框修剪为“传输方向”列中仅包含“下行链路”的行。附言如果有人能猜出为什么我没有看到预期的行为,请发表评论。

专门针对原始问题:

expr[grepl("hesc",expr$cell_type),]

expr[grepl("bj fibroblast|hesc",expr$cell_type),]

答案 6 :(得分:1)

似乎没有人包含which函数。它对于过滤也很有用。

expr[which(expr$cell == 'hesc'),]

这还将处理NA,并将其从结果数据帧中删除。

在9840上通过24个数据帧将其运行50000次,看来哪种方法比%in%方法运行时间快60%。

答案 7 :(得分:1)

这对我来说就像魔术一样。

celltype_hesc_bool = expr['cell_type'] == 'hesc'

expr_celltype_hesc = expr[celltype_hesc]

Check this blog post

答案 8 :(得分:0)

我们可以使用data.table库

  library(data.table)
  expr <- data.table(expr)
  expr[cell_type == "hesc"]
  expr[cell_type %in% c("hesc","fibroblast")]

或使用%like%运算符过滤以进行模式匹配

 expr[cell_type %like% "hesc"|cell_type %like% "fibroblast"]