用 dplyr 或 R 中的其他包进行子集化

subsetting with dplyr or other packages in R

所以我们有这个基本数据

A <- c(1,1,1,2,2,2,3,3,3)
B <- c(1,0,0,1,0,0,1,0,0)
C <- c(2,2,3,4,3,3,3,4,3)
Data <- data.frame(A,B,C)

我们现在要过滤它

我们查看每个 C=3 和 B=1 的情况 并找到它的值 使用此 A 值,我们要搜索 C=4 和 B=0 并将其删除

所以图形化,

我们要删除红色行并保留绿色行

理想情况下,我想使用 dplyr,但对其他替代方案持开放态度

你提到了其他选择,所以这里是data.table

library(data.table)
 d=as.data.table(Data)
 d[!((A==d[B==1 & C==3,A])&(C==4&B==0))]

但不确定这在需要删除更多行的更复杂的情况下如何工作。

Base R,我想这就是你需要的:

# Column A values to consider for filter
C3_B1 <- Data[Data$C==3 & Data$B==1,"A"]

# Filter out rows where C==4 and B==0
Data[ !(Data$A %in% C3_B1 &
          Data$C==4 &
          Data$B==0),]

# Output - row 8 is removed
#   A B C
# 1 1 1 2
# 2 1 0 2
# 3 1 0 3
# 4 2 1 4
# 5 2 0 3
# 6 2 0 3
# 7 3 1 3
# 9 3 0 3

使用 sqldf 包:

sqldf(c("DELETE FROM Data 
          WHERE A IN (SELECT A FROM Data 
                       WHERE  C = 3 AND B = 1) 
                AND C = 4 
                AND B = 0",
        "SELECT * FROM Data "))

dplyr

Data %>% filter(!(A==select(filter(Data, C==3 & B==1), A)[,1] & C==4 & B ==0))

它本质上是一个两步过程。

第一个是:

select(filter(Data, C==3 & B==1), A)

筛选 Data,其中 C==3B==1,然后 select 仅列 A。让我们将其命名为 temp.

第二步是:

Data %>% filter(!(A==temp[,1] & C==4 & B ==0))

一个简单的过滤。

另一个解决方案,可能比上面的一些慢一点。但对 reader 可能会更透明一些。如果您想 运行 B 和 C 的不同值,也更容易投入函数。

a_values <- Data %>% 
  filter(B == 1, C == 3) %>% 
  select(A) %>% 
  unique()

Data <- Data %>% 
  filter(!(A %in% a_values & B == 0 & C == 4))

编辑:忘了否定!

这是另一种 data.table 方法。首先,将其读入键控 data.table:

require(data.table)
DT <- data.table(Data,key="C,B,A")

确定 OP 不喜欢的 A 值

myA <- DT[J(3,1)]$A

排除

DT[!J(4,0,myA)]

如果 myA 是向量,这也适用。