有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

正则表达式如何匹配Java中规则匹配中不以英文字母开头的字符串中的所有数字组合

我有一根像

String str = "305556710S  or 100596269C OR CN111111111";

我只想匹配字符串中以数字开头或以数字开头,以英文字母结尾的字符, 然后在匹配字符的前面加上两个“?”人物。 我写了一篇像父亲一样的文章

    Pattern pattern = Pattern.compile("^[0-9]{1,10}[A-Z]{0,1}", Pattern.CASE_INSENSITIVE);
    Matcher matcher = pattern.matcher(str);
    while (matcher.find()) {
        int start = matcher.start();
        int end = matcher.end();
        String matchStr = matcher.group();
        System.err.println(matchStr);
    }

但它只能匹配第一个字符“3055556710S”。 但是如果我修改了模式

 Pattern pattern = Pattern.compile("[0-9]{1,10}[A-Z]{0,1}", Pattern.CASE_INSENSITIVE);

它将匹配“3055556710S”、“100596269C”、“111111111”。但“111111111”的前缀是英文字符“CN”,这不是我的目标。 我只想匹配“3055556710S”和“100596269C”并添加两个“?”匹配字符之前的字符。有人能帮我吗


共 (2) 个答案

  1. # 1 楼答案

    我认为你需要使用单词边界。尝试此更改的模式:

    "\\b[0-9]{1,10}[A-Z]{0,1}\\b"
    

    这将打印出:

    305556710S
    100596269C
    

    工作原理:

    1. 这里的区别在于,它将只检查一对单词边界内的字符序列。在前面使用的模式中,甚至从单词中间开始的字符序列也可用于与模式匹配,因此,来自CN1111...的偶数11111...与模式匹配并通过
    2. 单词边界也与字符串输入的结尾匹配。因此,即使候选词出现在行尾,它也会被拾取

    如果结尾可以出现多个英文字母,则删除最大出现次数指示符1。在这种情况下:

    "\\b[0-9]{1,10}[A-Z]{0,}\\b"
    
  2. # 2 楼答案

    首先,在这个特定的regexp中应该避免使用^。正如您所注意到的,您不能返回多个结果,因为“^”是“匹配字符串开头”的指令

    使用\b可以是一种解决方案,但可能会得到无效的结果。比如说

    305556710S or -100596269C OR CN111111111

    regexp"\\b[0-9]{1,10}[A-Z]{0,}\\b"将匹配100596269C(因为连字符不是单词字符,所以-和1之间有一个单词边界)

    下面的regexp与您想要的完全匹配:所有数字,后面可能跟一些英文字符,要么在字符串开头,要么在空格后面,要么在空格后面,要么在字符串末尾

    (?<=^| )[0-9]{1,10}[A-Z]*(?= |$)

    说明:

    1. (?<;=^ |)是一种落后。它确保在实际位置后面有^(字符串开始)或空格。请注意,lookbehinds不会将匹配字符添加到结果中:空格不会是结果的一部分
    2. [0-9]{1,10}[A-Z]*匹配数字(至少一个,最多十个),然后匹配一个或多个字母
    3. (?=|$)是一种前瞻。它确保在匹配后有空格或$(字符串结尾)。与lookbehinds一样,字符不会添加到结果中,并且位置保持不变:例如,此处读取的空间也可以被下一个捕获字符串的lookbehind读取

    例如:305556710S or 100596269C OR CN111111111匹配:在索引0[3055556710S]处,在索引15[100596269C]处100596269C123不匹配