目前,我有一个数据表,我想在R中分成两个独立的数据帧。为了做到这一点,我想循环一定数量的列并使用或声明。
例如:
>my_data<-fread("...csv")
>my_data
DOGS CATS PENGUINS TURTLES LIONS TIGERS
3 0 0 0 1 8
0 5 2 4 0 1
0 0 0 7 0 0
因此,例如,如果我想创建一个新的数据表,其中包含第2,3,4或6列中的值为0的行,我该怎么做?
目前我正在做
my_animals<-my_data[CATS==0 | PENGUINS==0 | TURTLES==0 | TIGERS ==0]
>my_animals
DOGS CATS PENGUINS TURTLES LIONS TIGERS
3 0 0 0 1 8
0 0 0 7 0 0
这是我想要的数据表但我的代码效率不高,我想稍后添加更多条件(即如果我有一个新列,我想添加FROGS == 0) 理想情况下,我想要使用列索引(因此我可以使用2:4而不是键入CATS,PENGUINS,TURTLES),但有没有办法缩短我的代码并使用列索引而不是列名?
答案 0 :(得分:2)
如果我们将您的data.frame
转换为df <- as.data.frame(my_data)
ind <- which(colSums(apply(df[c(2:4, 6)], 1, function(i) i == 0)) != 0)
df[ind,]
# DOGS CATS PENGUINS TURTLES LIONS TIGERS
#1 3 0 0 0 1 8
#3 0 0 0 7 0 0
,那么
$
答案 1 :(得分:1)
使用data.table的一种方法是使用rowSums
:
my_animals <- my_data[rowSums(my_data[, .SD,
.SDcols=c("CATS", "PENGUINS", "TURTLES", "TIGERS")] == 0) > 1, ]
这将返回所需的结果
my_animals
DOGS CATS PENGUINS TURTLES LIONS TIGERS
1: 3 0 0 0 1 8
2: 0 0 0 7 0 0
代码可以解释如下:
my_data[, .SD, .SDcols=c("CATS", "PENGUINS", "TURTLES", "TIGERS")]
子集data.table,选择所需的列。rowSums(...] == 0)
对data.table中每行等于0的元素进行求和rowSums(...] == 0) > 0
返回一个逻辑向量,其中至少有一个0的任何行对应于TRUE。my_data[rowSums(...]
在逻辑向量上设置my_data。正如@Sotos所提到的,可以在.SDcols
中使用列索引而不是它们的名称,如下所示:
my_data[rowSums(my_data[, .SD, .SDcols=c(2:4, 6)] == 0) > 1, ]
返回等效对象。