You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

R语言实现命名向量按字符模式分组求每组最大值

问题描述

假设我有如下命名向量:

test <- c("x1" = 0.1, "x2" = 0.3, "x3" = 0.4,
          "y1" = 0.1, "y2" = 0.5, "y3" = 0.4,
          "z1" = 0.5, "z2" = 0.3, "z3" = 0.4)

test
#  x1  x2  x3  y1  y2  y3  z1  z2  z3 
# 0.1 0.3 0.4 0.1 0.5 0.4 0.5 0.3 0.4

需求是按向量名称的字母前缀对元素分组,找出每组中取值最大的元素,本示例预期输出为"x3"、"y2"、"z1"。
注意:无法提前获知共有多少个不同的字母分组,也无法提前知道每个字母分组下包含多少个元素,需要简洁灵活、无需预先指定分组规则的代码实现。

实现方案

不需要提前硬编码分组规则,以下几种实现都可以满足需求,核心逻辑都是先自动提取名称的字母前缀作为分组键,再分组取最大值对应的元素名,自动适配任意数量的分组、任意长度的字母前缀、任意数量的组内元素:

基础R实现(无需加载第三方包)

用正则提取名称里的非数字前缀作为分组,配合基础分组函数计算即可:

# 提取名称中的字母前缀(自动剔除末尾所有数字部分)
group_key <- gsub("[0-9]+$", "", names(test))
# 自动分组取每组最大值对应的元素名
result <- tapply(seq_along(test), group_key, function(i) names(which.max(test[i])))
# 输出最终结果
unname(result)
# [1] "x3" "y2" "z1"

核心用到的函数:

  • gsub:通过正则匹配自动提取前缀,不管前缀是1个还是多个字母、后缀数字是几位都能适配
  • tapply:按分组键自动拆分索引,不需要提前知道分组总数
  • which.max:快速返回向量中最大值对应的位置,比排序取Top1的运行效率更高

dplyr实现(管道式易读写法)

如果习惯tidyverse语法,代码逻辑更直观,遇到同组并列最大值的场景也会自动保留所有匹配项:

library(dplyr)
data.frame(
  name = names(test),
  value = test,
  group = gsub("[0-9]+$", "", names(test))
) %>%
  group_by(group) %>%
  slice_max(value, n = 1) %>%
  pull(name)
# [1] "x3" "y2" "z1"

data.table实现(大向量性能最优)

如果处理长度百万级以上的命名向量,data.table的分组计算速度优势明显:

library(data.table)
data.table(
  name = names(test),
  value = test,
  group = gsub("[0-9]+$", "", names(test))
)[, .SD[which.max(value)], by = group]$name
# [1] "x3" "y2" "z1"

以上所有实现都不需要手动指定分组规则,新增分组、调整组内元素数量时不需要修改代码,可直接复用。


内容的提问来源于stack exchange,提问作者user321797

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.27 21:54:31