根据一系列变量过滤数据帧

时间:2017-09-28 13:22:43

标签: r loops dplyr apply

我的数据框有一系列变量c1...c20。每个变量都包含一个代码。我有一个代码矢量code.vec,我希望将数据框子集化,以包含c1|c2|c3|...|c20位于code.vec的记录。

示例数据(示例中仅使用3个cn变量):

code.vec<-c("T1", "T2", "T3", "T4")

c1<-c("T1", "X1", "T6", "R5")
c2<-c("R4", "C6", "C7", "X3")
c3<-c("C5", "C2", "X4", "T2")

df<-data.frame(c1, c2, c3)

这就是我目前正在做的事情:

library(dplyr)
df %>% filter(c1 %in% code.vec | c2 %in% code.vec | c3 %in% code.vec)

  c1 c2 c3
1 T1 R4 C5
2 R5 X3 T2

这很有效,但由于真实的数据帧有20个cn个变量,因此输入很多。看起来应该有一个简单的应用或循环解决方案(并且在SAS中使用数组和do循环很容易)但我无法在R中找到解决方案,我找不到任何类似的解决方案这里的问题。

2 个答案:

答案 0 :(得分:1)

以下是使用filter_all中的dplyr的简单解决方案:

library(dplyr)

df %>% 
  filter_all(any_vars(. %in% code.vec))

<强>结果:

  c1 c2 c3
1 T1 R4 C5
2 R5 X3 T2

在评论中提到,如果您希望过滤所有变量包含code.vec的行,则可以将any_vars替换为all_vars:< / p>

df %>% 
  filter_all(all_vars(. %in% code.vec))

答案 1 :(得分:0)

这是一种应该相对较快的方法。

# get the position of the rows that match using modulus (final row returns 0)
temp <- which(unlist(dat) %in% code.vec) %% nrow(dat)
# replace 0s with final row
temp[temp == 0] <- nrow(dat)

然后是子集

dat[unique(sort(temp)),]
  c1 c2 c3
1 T1 R4 C5
4 R5 X3 T2

请注意,我正在使用data.frame变量中的字符向量。如果您将它们存储为因素,则需要将unlist(dat)包裹在as.character()中。

数据

dat <-
structure(list(c1 = c("T1", "X1", "T6", "R5"), c2 = c("R4", "C6", 
"C7", "X3"), c3 = c("C5", "C2", "X4", "T2")), .Names = c("c1", 
"c2", "c3"), row.names = c(NA, -4L), class = "data.frame")