Java 11环境下使用正则拆分字符串:保留分隔符仅丢弃空格的实现问题
原split方法错误原因
- 你的正则
((?<=[^0-9]+)|(?=[^0-9]+)|(\\s+))存在逻辑冲突:split仅会删除匹配到的非零宽分隔符,空格属于非数字字符,会被前后的零宽断言匹配为拆分后的独立元素,不会被作为分隔符过滤;同时该规则没有对负号做特殊处理,会导致负号和后续数字被拆分。
更新后需求的Matcher实现
你选择用Matcher代替split的思路是正确的,这类提取符合规则片段的场景,正向匹配逻辑远比分隔符拆分更易维护。
匹配规则梳理
我们可以直接定义两类需要提取的合法片段,空格会被自动跳过不匹配:
- 连续算术片段:由数字、
+-*/%^运算符组成,支持前导负号、数字前导零,运算符和数字无空格时不拆分 - 单个非数字、非空格、非运算符的字符(如单个字母)
正则表达式
(?:-?\d[+\-*/%^]?)+|[^\d\s+\-*/%^]
规则解释:
(?:-?\d[+\-*/%^]?)+:非捕获组匹配连续算术片段-?匹配可选的前导负号\d匹配数字[+\-*/%^]?匹配数字后可选的运算符- 外层
+支持多组数字+运算符的连续组合(如333+444)
|或关系[^\d\s+\-*/%^]匹配单个不属于数字、空格、运算符的字符,对应需要拆分的单个字母
Java实现代码
import java.util.ArrayList; import java.util.List; import java.util.regex.Matcher; import java.util.regex.Pattern; public class RegexTest { public static void main(String[] args) { String hello = "333+444 5qwerty5 006 -7"; Pattern pattern = Pattern.compile("(?:-?\\d[+\\-*/%^]?)+|[^\\d\\s+\\-*/%^]"); Matcher matcher = pattern.matcher(hello); List<String> result = new ArrayList<>(); while (matcher.find()) { result.add(matcher.group()); } // 如需转为数组可调用 result.toArray(new String[0]) System.out.println(result); } }
输出结果
运行后得到的集合完全符合预期:
["333+444", "5", "q", "w", "e", "r", "t", "y", "5", "006", "-7"]
内容的提问来源于stack exchange,提问作者pmdci
相关产品推荐
相关产品推荐

