我有一组数据,其中第一列是一堆ID号码(有些重复),第二列只是一堆数字。我需要一种方法来仅基于第二列中最小的数字保留每个ID号码一次。
Row# ID Number
1 10 180
2 12 167
3 12 182
4 12 135
5 15 152
6 15 133
例如:我只想保留这里的第1行、第4行和第6行,并删除其余行。
我有一组数据,其中第一列是一堆ID号码(有些重复),第二列只是一堆数字。我需要一种方法来仅基于第二列中最小的数字保留每个ID号码一次。
Row# ID Number
1 10 180
2 12 167
3 12 182
4 12 135
5 15 152
6 15 133
例如:我只想保留这里的第1行、第4行和第6行,并删除其余行。
base R
选项是aggregate
。 使用aggregate
,我们可以使用“公式”方法或使用by
参数指定分组元素/变量的list
来指定分组方式。 使用“公式”方法,我们可以获取每个“ID”的“Number”的min
值。aggregate(Number~ID, df1, FUN=min)
或者我们可以使用更快的选项,使用data.table
。 在这里,我们将“data.frame”转换为“data.table”(setDT(df1)
),按“ID”分组,获取“Number”的min
值。
library(data.table)
setDT(df1)[, list(Number=min(Number)), by = ID]
或者也可以使用setorder
来对'Number'列进行排序,并使用具有by
选项的unique
选择第一个非重复的'ID'行。(来自@David Arenburgs的评论)
unique(setorder(setDT(df1), Number), by = "ID")
或者使用dplyr
,我们按'ID'进行分组并使用summarise
获取子集行。
library(dplyr)
df1 %>%
group_by(ID) %>%
summarise(Number= min(Number))
或者我们可以使用 sqldf
语法来获取数据的子集。library(sqldf)
sqldf('select ID,
min(Number) as Number
from df1
group by ID')
如果有多列数据,您想要获取每个“ID”中“Number”最小值所在的行,则可以使用which.min
. 使用.I
将获取行索引,然后可以用于子集化行。
setDT(df1)[df1[, .I[which.min(Number)], by = ID]$V1]
或者使用 dplyr
,我们使用 slice
来过滤掉每个 'ID' 中具有最小 'Number' 值的行。df1 %>%
group_by(ID) %>%
slice(which.min(Number))
或者
do.call(rbind,
lapply(split(df1, df1$ID), function(x) subset(x, Number == min(Number))))
#ID Number
#10 10 180
#12 12 135
#15 15 133
unique(setorder(setDT(df1), Number), by = "ID")
。我认为你需要用which.min
代替min
,因为似乎 OP 始终 想要保留每个ID
的一行。顺便说一句,很好的sqldf
解决方案 :) - David Arenburgmin
只保留單個值,但當有更多列時,which.min
將更為通用。 - akrun