如何在R语言(含tidyverse)中用正则表达式字典批量替换?
用R/tidyverse实现正则表达式批量替换
这个需求在处理多语言日期文本时特别实用,尤其是像你这样需要把波兰语月份缩写统一转成数字的场景。我会用两种方式帮你实现:tidyverse工具链(更简洁)和基础R方法(无需额外包)。
第一步:完善你的匹配字典
首先得把你的正则字典补全,加上对应的月份数字(我帮你补全了未写完的正则,你可以根据实际情况调整):
library(tidyverse) # 构建完整的月份匹配字典:正则表达式 → 对应数字 month_dict <- tibble( from = c( "(S|s)tycz(eń|nia)|(S|s)t(y|ycz)", "(L|l)ut(y|ego)|(L|l)u(t)", "(M|m)ar(ca|zec)|(M|m)ar", "(K|k)wie(tnia|cień)|(K|k)wi(|e)", "(M|m)aj(a|)", "(C|c)zerw(ca|iec)|(C|c)e(|r|rw)", "(L|l)ip(ca|iec)|(L|l)i(|p|c)", "(S|s)ierp(nia|ień)|(S|s)i(|e|er|erp)", "(W|w)rze(sień|śnia)|(W|w)rz(|e)", "(P|p)aź(dziernika|ździernik)|(P|p)a(|ź|źd)", "(L|l)is(topada|topad)|(L|l)i(|s|is)", "(G|g)rud(nia|zień)|(G|g)ru(|d)" ), to = as.character(1:12) )
方法一:用tidyverse的stringr包(推荐)
stringr里的str_replace_all()函数直接支持命名向量作为替换规则,一步就能完成批量替换:
# 把字典转成命名向量:名字是正则表达式,值是替换后的数字 month_replace_rules <- set_names(month_dict$to, month_dict$from) # 示例输入文本(包含各种波兰语月份写法) sample_text <- c( "Styczeń 2023", "lutego", "Marzec", "kwiecień", "maj", "Czerwiec", "lipiec", "sierpień", "wrzesień", "październik", "listopad", "grudzień", "St 2022", "Lu", "Mar", "Kwi", "Ce" ) # 执行批量替换 processed_text <- str_replace_all(sample_text, month_replace_rules) # 查看结果 print(processed_text)
运行后你会看到所有匹配的月份缩写/全称都被转换成了对应的数字,比如"Styczeń 2023"变成"1 2023","lutego"变成"2"。
方法二:基础R实现(无需额外包)
如果不想加载tidyverse,可以用Reduce()函数循环应用每个替换规则:
# 示例输入文本 sample_text <- c( "Styczeń 2023", "lutego", "Marzec", "kwiecień", "maj", "Czerwiec", "lipiec", "sierpień", "wrzesień", "październik", "listopad", "grudzień", "St 2022", "Lu", "Mar", "Kwi", "Ce" ) # 循环应用每个正则替换规则 processed_text_base <- Reduce(function(current_text, idx) { gsub(month_dict$from[idx], month_dict$to[idx], current_text) }, init = sample_text, seq_len(nrow(month_dict))) # 查看结果 print(processed_text_base)
注意事项
- 正则顺序:如果你的正则存在重叠匹配的情况,要注意规则的顺序(先匹配长模式,再匹配短模式),不过你的月份正则应该不会有这个问题。
- 大小写:你的正则已经包含了大小写匹配(比如
(S|s)),所以不管输入是大写还是小写开头都能匹配到。
内容的提问来源于stack exchange,提问作者Jacek Kotowski
相关产品推荐
相关产品推荐

