R data.table中的条件唯一计数
我想按组统计数据集中的冲突数。我觉得在data.table中必须有一种简单的方法来实现这一点,但似乎无法理解。我创建了一个虚拟变量,告诉我data.table的每一行是否存在冲突:R data.table中的条件唯一计数,r,data.table,R,Data.table,我想按组统计数据集中的冲突数。我觉得在data.table中必须有一种简单的方法来实现这一点,但似乎无法理解。我创建了一个虚拟变量,告诉我data.table的每一行是否存在冲突: testDT <- data.table(Name = c(rep('A',6),rep('B',5)), Division = c(rep(11,6),rep(12,5)), ID = c(205,205,NA,201,201
testDT <- data.table(Name = c(rep('A',6),rep('B',5)),
Division = c(rep(11,6),rep(12,5)),
ID = c(205,205,NA,201,201,201,203,203,203,204,NA),
Conflict = c(0,0,0,1,1,1,1,1,1,1,0))
我一直在考虑如何使用
sum(!is.na(unique(ID))
,但我不知道如何有条件地计算唯一值,而不在data.table的I部分创建条件(Conflict==1)
您可以根据data.table[]
中的条件对ID
变量进行子集划分,然后计算唯一值:
library(data.table)
testDT[, Count := uniqueN(ID[!is.na(ID) & Conflict == 1]), by=.(Name, Division)]
testDT
# Name Division ID Conflict Count
# 1: A 11 205 0 1
# 2: A 11 205 0 1
# 3: A 11 NA 0 1
# 4: A 11 201 1 1
# 5: A 11 201 1 1
# 6: A 11 201 1 1
# 7: B 12 203 1 2
# 8: B 12 203 1 2
# 9: B 12 203 1 2
# 10: B 12 204 1 2
# 11: B 12 NA 0 2
或者按照你的逻辑:
testDT[, Count := sum(!is.na(unique(ID[Conflict == 1]))), by=.(Name, Division)]
这里有一个带有
dplyr
library(dplyr)
testDT %>%
group_by(Name, Division) %>%
mutate(Count = n_distinct(ID[!is.na(ID) & Conflict==1]))
# Name Division ID Conflict Count
# <chr> <dbl> <dbl> <dbl> <int>
#1 A 11 205 0 1
#2 A 11 205 0 1
#3 A 11 NA 0 1
#4 A 11 201 1 1
#5 A 11 201 1 1
#6 A 11 201 1 1
#7 B 12 203 1 2
#8 B 12 203 1 2
#9 B 12 203 1 2
#10 B 12 204 1 2
#11 B 12 NA 0 2
库(dplyr)
testDT%>%
按(姓名、部门)分组%>%
mutate(Count=n_distinct(ID[!is.na(ID)&Conflict==1]))
#名称分区ID冲突计数
#
#1A 1120501
#2 A 11 205 0 1
#3 A 11 NA 0 1
#4 A 11 201 1 1
#5 A 11 201 1 1
#6 A 11 201 1
#7 B 12 203 1 2
#8 B 12 203 1 2
#9 B 12 203 1 2
#10B1220412
#11 B 12 NA 0 2
为什么条件在j
内?我想会慢一些testDT[!is.na(ID)&Conflict==1,Count:=uniqueN(ID),by=(Name,Division)]
对整个表执行所有逻辑测试,而不是对每个组执行测试。除非我看不到什么。这将为这些行分配NA
s。取决于@shughes,如果这很重要的话……哦,还有一件事uniqueN
有一个na.rm
参数,因此您可以使用它来代替条件作用!是的。不过,根据您使用的版本,这可能会给您带来一个bug。(我必须更新才能通过它)
library(dplyr)
testDT %>%
group_by(Name, Division) %>%
mutate(Count = n_distinct(ID[!is.na(ID) & Conflict==1]))
# Name Division ID Conflict Count
# <chr> <dbl> <dbl> <dbl> <int>
#1 A 11 205 0 1
#2 A 11 205 0 1
#3 A 11 NA 0 1
#4 A 11 201 1 1
#5 A 11 201 1 1
#6 A 11 201 1 1
#7 B 12 203 1 2
#8 B 12 203 1 2
#9 B 12 203 1 2
#10 B 12 204 1 2
#11 B 12 NA 0 2