我有两个不同的数据帧,格式如下:
DF1 -
v1 v2 v3 v4 v5
a 1 2 +
b 5 2 + +
c 5 2 + +
d 4 3 + +
e 1 5 + +
f 3 5
g 4 2
h 3 1
i 5 5 + +
DF2 -
v1 v2 v3 v4
a 1 2 +
b 5 2 + +
c 5 2 +
d 4 3 +
e 1 5 +
f 3 5
g 4 2
h 3 1
i 5 5 +
我的脚本给出了v1的散点图&v2,但首先要删除在v3-v4或v3-v5中至少有一个"+"的行。
我的数据帧可以用更多的v1-v2对更大,但总是有带有"+"的v3-v4或v3-v5列。我手动调整代码以指定要绘制的列和要删除的行,这取决于我正在处理的DF格式。
它工作得很好,但我想使脚本更具交互性,如下所示:
# Select v3-v4 or v3-v5 via interactive gui to give vector of column headers.
remove.vars.vector <- select.list(names(DF), # Select columns as vector of column header names via interactive gui.
multiple = TRUE, # Can choose multiple columns.
title = "Choose variables to remove from data set", # Title on gui.
graphics = TRUE) # Allow launch of gui.
# Return columns from DF with this vector of column headers.
remove.vars.subset <- DF[remove.vars.vector]
# Return rows that have at least one "+" in v3-v4 or v3-v5.
remove.vars.subset.+ <- subset(DF, remove.vars.subset == "+")
# Removes all rows that contain >=1 NA.
complete.data.+ <- remove.vars.subset.+[complete.cases(remove.vars.subset.+), ]
# Combine by rows "complete.data.+" with DF.
combo.list <- rbind(DF,complete.data.+)
# Remove duplicate rows from combined data frame.
complete.data <- combo.list[!duplicated(combo.list, fromLast = FALSE) & !duplicated(combo.list, fromLast = TRUE),]
问题:上面的代码没有完全剥离在v3-4或v3-5中包含至少一个"+"的行的数据帧。问题似乎是这几行:
# Return rows that have at least one "+" in v3-v4 or v3-v5.
remove.vars.subset.+ <- subset(DF, remove.vars.subset == "+")
我也得到一些行在最后只有NA在每个单元格因此完成。下一行代码中的case。
因此,最终的数据帧在版本3-4或版本3-5中仍然包含一些带"+"的行。
:
是否有更好的方法来子集行在数据帧使用的列标题的矢量,可能包含"+"在他们的行?
提前谢谢你。
编辑 - 2016/08/09 - 18:54我只是注意到一些我没有澄清的关于我的数据框架的事情。在v3-v4或v3-v5中,有些行没有"+"。这些是我最终想要保留的行,这样我就可以绘制散点。我已经相应地编辑了数据帧。我只是在看答案,试图理解它们。我对R还是个新手。
假设数据DF
为
> DF
v1 v2 v3 v4 v5
1 1 2 +
2 5 2 + +
3 5 2 + +
4 4 3 + +
5 1 5 + +
我选v3
和v4
。那么remove.vars.subset
,按照您的代码,是
> remove.vars.subset
v3 v4
1 +
2 + +
3 +
4 +
5 +
,注意remove.vars.subset == "+"
的计算结果为
> remove.vars.subset == "+"
v3 v4
[1,] TRUE FALSE
[2,] TRUE TRUE
[3,] TRUE FALSE
[4,] FALSE TRUE
[5,] TRUE FALSE
subset
然后做的是要求R
从条件计算为TRUE
的数据框中返回行,即:
DF[c(TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE),]
连接第一列和第二列。但是数据框中只有5行,而逻辑向量中有10个元素。由于DF
只有5行,因此附加了NA
s(因此好像DF
有10行),并相应地计算表达式。所以你看:
> subset(DF, remove.vars.subset == "+")
v1 v2 v3 v4 v5
1 1 2 +
2 5 2 + +
3 5 2 + +
5 1 5 + +
NA NA NA <NA> <NA> <NA>
NA.1 NA NA <NA> <NA> <NA>
你可能想试试
DF[!apply(remove.vars.subset, MAR=1, function(x) any(x=="+")), ]
> DF[!apply(remove.vars.subset, MAR=1, function(x) any(x=="+")), ]
[1] v1 v2 v3 v4 v5
<0 rows> (or 0-length row.names)
不返回任何行,因为所有行(给定v3
和v4
的选择)中至少有一个"+"。但是假设我们选择了v4
和v5
:
> DF[!apply(remove.vars.subset, MAR=1, function(x) any(x=="+")), ]
v1 v2 v3 v4 v5
1 1 2 +
我有一个解决方案,你不选择列,但所有行与"+"和NAs从数据框中删除。我不知道这是否有帮助。它基于以下问题:更好的方法来过滤数据帧与dplyr使用或?
v1 <- c(1,2,3,4,5,NA)
v2 <- c(1,2,3,4,5,NA)
v3 <- c("","+","+","","",NA)
v4 <- c("","+","","+","",NA)
v5 <- c("","+","","","",NA)
D1 <- cbind.data.frame(v1,v2,v3,v4,v5,stringsAsFactors=F)
library(dplyr)
remove.vars.vector <- c("v3","v4","v5")
condition <- c("+",NA)
D1 %>%
filter(rowSums(sapply(D1, FUN = "%in%", condition)) == 0) -> D1_new
编辑:我找到了选择列的可能性,不幸的是,我没有找到通过字符向量选择列的解决方案:
D1 %>% select_(remove.vars.vector) -> D1_sub # NOT working
D1 %>% select(v3:v5) -> D1_sub # working
D1 %>% select(v3,v4,v5) -> D1_sub # working
D1 %>% select_("v3","v4","v5") -> D1_sub # working
D1 %>%
filter(rowSums(sapply(D1_sub, FUN = "%in%", condition)) == 0) -> D1_new