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

在R中为数据框新增列:判断三列最大值对应类别

在R数据框中新增列获取最大值对应的类别

需要给数据框primary_game_fb新增一列primary_fb,取值为ff_num、si_num、fc_num三列中数值最大的列对应的类别(分别对应"FF"、"SI"、"FC")。

数据样例:

head(primary_game_fb, n = 20)
    pitcher game_date  ff_num si_num fc_num
     <dbl> <date>      <dbl>  <dbl>  <dbl>
 1  405395 2022-05-15      0      0      0
 2  424144 2022-04-07      1      8      0
 3  424144 2022-04-08      1      2      0
 4  424144 2022-04-13      0      2      0
 5  424144 2022-04-17      0     10      0
 6  424144 2022-04-19      0      4      0
 7  424144 2022-04-22      0     11      0
 8  424144 2022-04-24      1      6      0
 9  425794 2022-04-07      6     28     15
10  425794 2022-04-14      8     22     20
11  425794 2022-04-19      3     25     27
12  425794 2022-04-24      7     28     20
13  425794 2022-04-29     10     26     21
14  425794 2022-05-04      8     28     24
15  425794 2022-05-15      6     31     17
16  425794 2022-05-20     10     25     19
17  425794 2022-05-26     14     25     27
18  425794 2022-05-31     25     30     21
19  425794 2022-06-05     11     30     25
20  425794 2022-06-11      6     37     34

尝试的方法及问题

方法1:使用case_when

代码:

primary_game_fb <- primary_game_fb %>%
  dplyr::mutate(primary_fb = case_when(ff_num > si_num & fc_num ~ "FF",
                                       si_num > ff_num & fc_num ~ "SI",
                                       fc_num > ff_num & si_num ~ "FC",
                                       TRUE ~ NA_real_))

报错信息:

Error in `dplyr::mutate()`:
! Problem while computing `primary_fb = case_when(...)`.
Caused by error in `` names(message) <- `*vtmp*` ``:
! 'names' attribute [1] must be the same length as the vector [0]

错误原因:

  • 逻辑表达式写法错误:& fc_num实际是判断fc_num是否为非0值,而非ff_num > fc_num,正确逻辑应为ff_num > si_num & ff_num > fc_num。
  • 类型不匹配:NA_real_是数值型NA,但前面返回的是字符型字符串,需改用NA_character_。

方法2:使用嵌套ifelse

代码:

primary_game_fb <- primary_game_fb %>%
  dplyr::mutate(primary_fb = ifelse(ff_num > si_num & fc_num, "FF",
                                    ifelse(si_num > ff_num & fc_num, "SI",
                                           ifelse(fc_num > ff_num & si_num, "FC", NA))))

问题:无报错但结果不符合预期,比如第5行si_num=10远大于另外两列的0,但primary_fb返回NA。
原因:同样是逻辑条件错误,以si_num > ff_num & fc_num为例,& fc_num等价于& (fc_num != 0),第5行fc_num=0导致整个条件变为TRUE & FALSE,最终进入最后分支返回NA。

正确解决方案

方案1:修正逻辑条件的case_when

明确每个条件为当前列数值大于另外两列,同时统一NA类型并处理多列相等的情况:

primary_game_fb <- primary_game_fb %>%
  dplyr::mutate(primary_fb = case_when(
    ff_num > si_num & ff_num > fc_num ~ "FF",
    si_num > ff_num & si_num > fc_num ~ "SI",
    fc_num > ff_num & fc_num > si_num ~ "FC",
    # 处理两列最大值相等的情况,可自定义优先级
    ff_num == si_num & ff_num > fc_num ~ "FF",
    si_num == fc_num & si_num > ff_num ~ "SI",
    ff_num == fc_num & fc_num > si_num ~ "FC",
    # 全0或三列相等时返回NA
    TRUE ~ NA_character_
  ))

方案2:使用max.col函数(更简洁高效)

max.col可直接返回每行最大值所在的列索引,再通过索引匹配对应的类别:

primary_game_fb <- primary_game_fb %>%
  dplyr::mutate(
    # 获取最大值所在列的索引,ties.method处理多列相等的情况
    max_col = max.col(select(., ff_num, si_num, fc_num), ties.method = "first"),
    # 匹配类别,全0时返回NA
    primary_fb = case_when(
      ff_num == 0 & si_num == 0 & fc_num == 0 ~ NA_character_,
      TRUE ~ c("FF", "SI", "FC")[max_col]
    ),
    # 可选:删除中间生成的max_col列
    .keep = "unused"
  )
  • ties.method参数说明:
    • "first":优先选择第一个出现的最大值列
    • "last":优先选择最后一个出现的最大值列
    • "random":随机选择一个最大值列

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.24 12:03:22