我有一个包含字符串和数字的 df 。我需要按组过滤最大值,不包括年份(日期类型)。
我这样做了:
test
type Process RegionName Time Level a b c d e f g h i j k l m n o p q r s t u v w
a1 XYZ_1 ABC 2010 fixed 0 0 0 0 0 0 1 957 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
a1 XYZ_2 ABC 2010 fixed 0 0 0 0 0 0 0 61 0 0 0 3 0 0 0 0 0 0 0 0 0 0 0
a1 XYZ_3 ABC 2010 fixed 0 0 0 0 0 0 0 695 0 0 0 0 0 2 0 0 0 0 0 0 0 0 0
a1 XYZ_4 ABC 2010 fixed 0 0 0 0 0 0 0 525 0 0 0 0 0 0 0 3 0 0 0 0 0 0 0
b1 XYZ_5 ABC 2010 fixed 0 0 0 0 0 0 10551 1168053 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
b1 XYZ_6 ABC 2010 fixed 0 0 0 0 0 0 0 7571 0 0 0 30 0 0 0 0 0 0 0 0 0 0 0
b1 XYZ_7 ABC 2010 fixed 0 0 0 0 0 0 0 10883 0 0 0 0 0 51 0 0 0 0 0 0 0 0 0
b1 XYZ_8 ABC 2010 fixed 0 0 0 0 0 0 0 40453 0 0 0 0 0 0 0 196 0 0 0 0 0 0 0
b1 XYZ_9 ABC 2010 fixed 0 0 0 0 0 0 0 24464 0 0 0 0 0 0 0 0 0 0 0 0 0 0 53
c1 XYZ_10 ABC 2010 fixed 0 0 0 0 0 0 0 0 0 0 0 16 0 0 0 0 0 0 0 0 0 0 0
c1 XYZ_11 ABC 2010 fixed 0 0 0 0 0 0 0 129 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
d1 XYZ_12 ABC 2010 fixed 0 0 0 0 0 0 2 1616 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
d1 XYZ_13 ABC 2010 fixed 0 0 0 0 0 0 0 762 0 0 4 0 0 0 0 0 0 0 0 0 0 0 0
d1 XYZ_14 ABC 2010 fixed 0 0 0 0 0 0 0 1002 0 0 0 12 0 0 0 0 0 0 0 0 0 0 0
d1 XYZ_15 ABC 2010 fixed 0 0 0 0 0 0 0 556 0 0 0 0 0 7 0 0 0 0 0 0 0 0 0
d1 XYZ_16 ABC 2010 fixed 0 0 0 0 0 0 0 961647 0 0 0 0 0 0 0 4661 0 0 0 0 0 0 0
d1 XYZ_17 ABC 2010 fixed 0 0 0 0 0 0 0 1381 0 0 0 0 0 0 0 0 0 0 0 0 0 0 3
max_test <- test %>%
group_by(type) %>%
slice(which.max(a:w))
max_test
type Process RegionName Time Level a b c d e f g h i j k
a1 XYZ_1 ABC 2010 fixed 0 0 0 0 0 0 1 957 0 0 0
b1 XYZ_5 ABC 2010 fixed 0 0 0 0 0 0 10551 1168053 0 0 0
c1 XYZ_10 ABC 2010 fixed 0 0 0 0 0 0 0 0 0 0 0
d1 XYZ_12 ABC 2010 fixed 0 0 0 0 0 0 2 1616 0 0 0
a1 和 b1 是我所期望的。然而,c1 和 d1 不是。
对于 c1,我期望 XYZ_11 因为 129 > 16
对于 d1,我期望 XYZ_16 因为 961647 > 1616
知道我做错了什么吗?
注意:我没有在代码中引入以避免时间值。我只做which.max(a:w)。那么,a1 可能会考虑 2010 年而不是 957 作为最高值?
你想要这个:
df %>% filter(if_any(a:w, ~.x == max(across(a:w))), .by = type)
# A tibble: 4 × 28
type Process RegionName Time Level a b c d e f g
<chr> <chr> <chr> <int> <chr> <int> <int> <int> <int> <int> <int> <int>
1 a1 XYZ_1 ABC 2010 fixed 0 0 0 0 0 0 1
2 b1 XYZ_5 ABC 2010 fixed 0 0 0 0 0 0 10551
3 c1 XYZ_11 ABC 2010 fixed 0 0 0 0 0 0 0
4 d1 XYZ_16 ABC 2010 fixed 0 0 0 0 0 0 0
# ℹ 16 more variables: h <int>, i <int>, j <int>, k <int>, l <int>, m <int>,
# n <int>, o <int>, p <int>, q <int>, r <int>, s <int>, t <int>, u <int>,
# v <int>, w <int>
slice
,根据文档:
允许您按行(整数)位置对行进行索引。
不确定为什么你想用它来过滤。如果您不知道,请使用过滤器功能进行过滤。 阅读手册
在
matrixStats::rowMaxs
中使用 by
。
by(dat, dat$ype, \(x) {
x[which.max(matrixStats::rowMaxs(as.matrix(x[-(1:5)]))), ]
}) |> do.call(what='rbind')
# ype Process RegionName Time Level a b c d e f g h i j k l m n o p q r s t u v w
# a1 a1 XYZ_1 ABC 2010 fixed 0 0 0 0 0 0 1 957 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
# b1 b1 XYZ_5 ABC 2010 fixed 0 0 0 0 0 0 10551 1168053 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
# c1 c1 XYZ_11 ABC 2010 fixed 0 0 0 0 0 0 0 129 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
# d1 d1 XYZ_16 ABC 2010 fixed 0 0 0 0 0 0 0 961647 0 0 0 0 0 0 0 4661 0 0 0 0 0 0 0
数据:
dat <- structure(list(ype = c("a1", "a1", "a1", "a1", "b1", "b1", "b1",
"b1", "b1", "c1", "c1", "d1", "d1", "d1", "d1", "d1", "d1"),
Process = c("XYZ_1", "XYZ_2", "XYZ_3", "XYZ_4", "XYZ_5",
"XYZ_6", "XYZ_7", "XYZ_8", "XYZ_9", "XYZ_10", "XYZ_11", "XYZ_12",
"XYZ_13", "XYZ_14", "XYZ_15", "XYZ_16", "XYZ_17"), RegionName = c("ABC",
"ABC", "ABC", "ABC", "ABC", "ABC", "ABC", "ABC", "ABC", "ABC",
"ABC", "ABC", "ABC", "ABC", "ABC", "ABC", "ABC"), Time = c(2010L,
2010L, 2010L, 2010L, 2010L, 2010L, 2010L, 2010L, 2010L, 2010L,
2010L, 2010L, 2010L, 2010L, 2010L, 2010L, 2010L), Level = c("fixed",
"fixed", "fixed", "fixed", "fixed", "fixed", "fixed", "fixed",
"fixed", "fixed", "fixed", "fixed", "fixed", "fixed", "fixed",
"fixed", "fixed"), a = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), b = c(0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), c = c(0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L), d = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L), e = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), f = c(0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), g = c(1L,
0L, 0L, 0L, 10551L, 0L, 0L, 0L, 0L, 0L, 0L, 2L, 0L, 0L, 0L,
0L, 0L), h = c(957L, 61L, 695L, 525L, 1168053L, 7571L, 10883L,
40453L, 24464L, 0L, 129L, 1616L, 762L, 1002L, 556L, 961647L,
1381L), i = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L), j = c(0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), k = c(0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 4L, 0L, 0L, 0L, 0L),
l = c(0L, 3L, 0L, 0L, 0L, 30L, 0L, 0L, 0L, 16L, 0L, 0L, 0L,
12L, 0L, 0L, 0L), m = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), n = c(0L, 0L, 2L, 0L, 0L,
0L, 51L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 7L, 0L, 0L), o = c(0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L), p = c(0L, 0L, 0L, 3L, 0L, 0L, 0L, 196L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 4661L, 0L), q = c(0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), r = c(0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L
), s = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L), t = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), u = c(0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), v = c(0L,
0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L), w = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 53L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 3L)), class = "data.frame", row.names = c(NA,
-17L))
由
subset
提供的基本 R 选项,其中 ave
+ pmax
subset(
test,
!!ave(
do.call(pmax, test[-(1:5)]),
type,
FUN = \(x) which.max(x) == seq_along(x)
)
)
这给出了
type Process RegionName Time Level a b c d e f g h i j k l m n o
1 a1 XYZ_1 ABC 2010 fixed 0 0 0 0 0 0 1 957 0 0 0 0 0 0 0
5 b1 XYZ_5 ABC 2010 fixed 0 0 0 0 0 0 10551 1168053 0 0 0 0 0 0 0
11 c1 XYZ_11 ABC 2010 fixed 0 0 0 0 0 0 0 129 0 0 0 0 0 0 0
16 d1 XYZ_16 ABC 2010 fixed 0 0 0 0 0 0 0 961647 0 0 0 0 0 0 0
p q r s t u v w
1 0 0 0 0 0 0 0 0
5 0 0 0 0 0 0 0 0
11 0 0 0 0 0 0 0 0
16 4661 0 0 0 0 0 0 0