按逻辑条件过滤data.frame行

lha*_*hne 145 r subset dataframe

我想data.frame根据逻辑条件从a中过滤行.我们假设我有数据框

   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
Run Code Online (Sandbox Code Playgroud)

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

   expr_value     cell_type
1    5.929771          hesc
2    5.873096          hesc
3    5.665857          hesc
Run Code Online (Sandbox Code Playgroud)

或者细胞类型"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
Run Code Online (Sandbox Code Playgroud)

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

我试过了:

expr[expr[2] == 'hesc']
# [1] "5.929771" "5.873096" "5.665857" "hesc"     "hesc"     "hesc"    
Run Code Online (Sandbox Code Playgroud)

如果原始数据框被称为"expr",但它会以错误的格式给出结果,如您所见.

lea*_*rnr 197

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

expr[expr$cell_type == "hesc", ]
Run Code Online (Sandbox Code Playgroud)

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

expr[expr$cell_type %in% c("hesc", "bj fibroblast"), ]
Run Code Online (Sandbox Code Playgroud)

  • 请注意,`==`函数将获取任何NA记录以及"hesc",而`%in%`则不会. (26认同)

rcs*_*rcs 84

使用subset(交互使用)

subset(expr, cell_type == "hesc")
subset(expr, cell_type %in% c("bj fibroblast", "hesc"))
Run Code Online (Sandbox Code Playgroud)

或更好 dplyr::filter()

filter(expr, cell_type %in% c("bj fibroblast", "hesc"))
Run Code Online (Sandbox Code Playgroud)

  • 小心!`subset`的文档有一个很大的警告:"这是一个便于交互使用的便利函数.对于编程,最好使用[,特别是参数*子集*的非标准子集函数]等标准子集函数可能会有意想不到的后果." (37认同)

Ken*_*ams 32

原因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
Run Code Online (Sandbox Code Playgroud)


nat*_*ood 22

你可以使用这个dplyr包:

library(dplyr)
filter(expr, cell_type == "hesc")
filter(expr, cell_type == "hesc" | cell_type == "bj fibroblast")
Run Code Online (Sandbox Code Playgroud)


eig*_*foo 7

似乎没有人包含 which 函数。它也可以证明对过滤很有用。

expr[which(expr$cell == 'hesc'),]
Run Code Online (Sandbox Code Playgroud)

这也将处理 NA 并将它们从结果数据帧中删除。

在 9840 x 24 数据帧上运行 50000 次,似乎 which 方法的运行时间比 %in% 方法快 60%。


小智 5

我正在处理一个数据框并且对提供的答案没有运气,它总是返回 0 行,所以我找到并使用了 grepl:

df = df[grepl("downlink",df$Transmit.direction),]
Run Code Online (Sandbox Code Playgroud)

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

具体到原来的问题:

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

expr[grepl("bj fibroblast|hesc",expr$cell_type),]
Run Code Online (Sandbox Code Playgroud)