R语言将两列字符型数据分箱生成新增字符列的实现方法
R 两列字符字段拼接生成用户类型列的实现方法
原代码异常原因
之前的代码出现重复列、运行不符合预期,核心是三处语法错误:
- 管道传入对象错误:
%>%会将前序对象作为第一个参数传入后续函数,代码开头取df1$type_of_users传入mutate,本质是操作一个不存在的空向量,没有对完整数据集df1做修改 - mutate参数格式错误:mutate新增列需要明确指定
列名 = 取值逻辑,原代码没有给case_when的输出指定列名,会自动生成异常命名的新列 - 冗余取值写法:dplyr管道环境内可直接调用数据框列名,反复写
df1$取列容易触发取值错位、重复列问题
正确实现方案
所有方案生成的type_of_users列class和mode均为character类型,可覆盖全部4种组合场景。
方案1:dplyr最简拼接(推荐)
不需要逐一枚举组合规则,直接做字符串处理拼接即可,后续如果新增车型/用户类型也不需要改代码:
library(dplyr) df1 <- df1 %>% mutate( type_of_users = paste0(member_casual, "_", sub("_bike", "", rideable_type)) )
规则校验:当rideable_type取值为electric_bike、member_casual取值为member时,会自动生成
member_electric;docked_bike对应生成xx_docked格式取值,完全匹配需求。
方案2:修正后的case_when写法
如果需要明确枚举所有组合规则(方便后续新增特殊映射),可以用修正语法后的case_when:
library(dplyr) df1 <- df1 %>% mutate( type_of_users = case_when( member_casual == 'casual' & rideable_type == 'docked_bike' ~ 'casual_docked', member_casual == 'member' & rideable_type == 'docked_bike' ~ 'member_docked', member_casual == 'casual' & rideable_type == 'electric_bike' ~ 'casual_electric', member_casual == 'member' & rideable_type == 'electric_bike' ~ 'member_electric' ) )
方案3:基础R实现(无需加载第三方包)
不使用dplyr的情况下,用R原生函数即可完成:
# 字符串拼接写法(和方案1逻辑一致) df1$type_of_users <- paste0(df1$member_casual, "_", sub("_bike", "", df1$rideable_type)) # 嵌套ifelse写法(和case_when逻辑一致) df1$type_of_users <- with(df1, ifelse( member_casual == 'casual' & rideable_type == 'docked_bike', 'casual_docked', ifelse(member_casual == 'member' & rideable_type == 'docked_bike', 'member_docked', ifelse(member_casual == 'casual' & rideable_type == 'electric_bike', 'casual_electric', 'member_electric')) ))
补充说明:
if/ifelse可以实现该需求(如方案3的嵌套ifelse写法),但stack()函数的适用场景是多列数据合并为长表结构,无法完成当前列值按行拼接的需求,不推荐使用。
生成列之后可运行class(df1$type_of_users)、mode(df1$type_of_users)校验类型,返回结果均为character即符合要求。
内容的提问来源于stack exchange,提问作者BlueBunny7788
相关产品推荐
相关产品推荐

