R语言如何正确统计非列表项格式的数字出现频率?
问题分析与修正方案
原代码的核心问题
- 拆分小数为多个整数统计:原正则用
\\d+仅匹配独立整数,会把10.5这类小数拆成10和5两个部分计数,导致第四个测试用例错误统计为2个,而实际应算1个。 - 排除逻辑错误:
- 字符类
[\\.\\b]中的\\b是退格符,不是单词边界,导致排除“数字+. ”的逻辑完全失效; - 未覆盖方括号
]的排除场景,导致20]里的20被错误统计; - 两个独立断言
(?![\\.\\b])和(?![\\)])的写法冗余且不准确,应合并为统一的排除断言。
- 字符类
- 未单独处理带%的数字:原正则没有将带
%的数字作为整体匹配,逻辑上未明确区分这类数字,存在潜在的匹配错误风险。
修正后的代码
library(stringr) test <- c("25 1) 10) 15) 20] 10%", "1. 1.", "110 20 30", "1. 10.5", "one two") # 正则分支说明: # 1. 匹配文本数字one/two # 2. 匹配带%的整数/小数(如10%、10.5%) # 3. 匹配整数/小数,且后面不能紧跟.、)、] str_count(test, "one|two|\\d+(?:\\.\\d+)?%|\\d+(?:\\.\\d+)?(?!\\.|[)\\]])")
执行后输出:
[1] 2 0 3 1 2
完全符合期望结果。
正则各部分解释
one|two:直接匹配文本数字;\\d+(?:\\.\\d+)?%:匹配带%的数字,\\d+匹配整数部分,(?:\\.\\d+)?可选匹配小数部分(非捕获组避免额外分组),最后匹配%;\\d+(?:\\.\\d+)?(?!\\.|[)\\]]):匹配普通整数/小数,(?!\\.|[)\\]])是正向否定断言,确保数字后面没有紧跟.、)或],排除列表项式数字。
内容的提问来源于stack exchange,提问作者Samarth A
相关产品推荐
相关产品推荐

