Java Pattern Matcher错误地匹配子字符串

时间:2018-06-14 12:08:49

标签: java regex pattern-matching matcher

我在特定文件路径中有一个文件夹列表 当通过下面的鳕鱼搜索时,它会给出以下文件列表

File[] fileList = folderListLocation.listFiles(someFileFilter);
//it gives following list
fileList=[NUTS, BOLTS, CAR_COMPONENTS_ADT,CAR_COMPONENTS_ADT1, WINDSHIELD]

现在我正在尝试计算一个特定名称的文件夹,这意味着如果我使用模式匹配器查找CAR_COMPONENTS_ADT,它应该给我数为2,如果我使用模式匹配器寻找NUTS,我应该计算为1

现在我使用以下代码将此文件列表与以下代码中的某些模式进行匹配

 int count=0;
 Pattern pattern = Pattern.compile(patternName);

for(File f: fileList){
Matcher matcher = pattern.matcher(f.getName());
if(matcher.find()){
        count++;
    }
}

现在在正常的情况下,这工作正常,如果patternName =“BIRD”,它将不匹配文件列表和

的最终值
 count will be 0

但如果patternName =“CAR_COMPONENTS”,则会产生

  count as 2

所以我不明白的是,模式匹配器如何匹配“CAR_COMPONENTS”与“CAR_COMPONENTS_ADT”和“CAR_COMPONENTS_ADT1”。即使它是一个子字符串,但我正在寻找完全匹配而不是部分。

非常欢迎建议和改进。提前致谢

2 个答案:

答案 0 :(得分:1)

只有在没有用字母/下划线括起来时才想匹配一个术语。

使用

int count=0;
Pattern pattern = Pattern.compile("(?<![_\\p{L}])" + patternName + "(?![_\\p{L}])");
for(File f: fileList) {
    Matcher matcher = pattern.matcher(f.getName());
    if(matcher.find()){
        count++;
    }
}

请参阅regex demo with CAR_COMPONENTS_ADTa regex demo with CAR_COMPONENTS

(?<![_\p{L}])是一个负面的lookbehind,匹配字符串中不会立即加上_或任何字母的位置(将\p{L}替换为[A-Za-z]或{{ 1}}仅匹配ASCII字母)如果在当前位置右侧有一个字母或\p{Alpha},则(?![_\p{L}])是一个未通过匹配的否定前瞻。

答案 1 :(得分:0)

这里有两个问题:

  1. Pattern.matcher的正则表达式不会查找完整字符串,除非您添加前导^(正则表达式的开头)和尾随$(正则表达式结束)。
  2. file.getName()将返回包含文件扩展名的名称。
  3. 因此,有两种可能的解决方案:

    1)你可以改变模式的正则表达式,这样匹配只匹配完整的文件名:

    int count=0;
    Pattern pattern = Pattern.compile("^" + patternName + "\\.?.+$");
    for(File f: fileList){
      Matcher matcher = pattern.matcher(f.getName());
      if(matcher.find()){
        count++;
      }
    }
    

    正则表达式的简短说明:

    ^NUTS\\.?.+$
    ^          $    # Start and end of the regex, to match the entire file-name
     NUTS           # The file name you want to check
         \\.?.*     # An (optional) file extension (i.e. `.txt`)
    

    2)您可以删除该扩展程序,然后使用.equals

    int count=0;
    for(File f: fileList){
      String fileNameWithoutExtension = f.getName().split("\\.")[0];
      if(patternName.equals(fileNameWithoutExtension)){
        count++;
      }
    }