正则表达式只匹配一些文件名

时间:2015-07-27 15:46:03

标签: c++ regex c++11

使用std :: regex并给出文件路径,我想只匹配以.txt结尾且不属于_test.txt.txtTEMP形式的文件名。任何其他下划线都没问题。

所以,例如:

  • somepath/testFile.txt应匹配。
  • somepath/test_File.txt应匹配。
  • somepath/testFile_test.txt不应该匹配。
  • somepath/testFile.txtTEMP不应该匹配。

这种模式的正确正则表达式是什么?

我尝试了什么:

(.*?)(\.txt) --->这匹配任何以.txt结尾的文件路径。

要排除包含_test的文件,我尝试使用否定外观:

(.*?)(?!_test)(\.txt)

但它不起作用。

我也尝试了负面的lookbehind,但MSVC14(Visual Studio 2015)在创建正则表达式时抛出std::regex_error异常,因此我不确定它是否不受支持或者我使用了错误的语法。

4 个答案:

答案 0 :(得分:2)

根据您发布的内容,使用此模式

^(?!.*_).*\.txt$

Demo

或基于OP编辑的此模式

^(.*(?<!_test)\.txt$)

Demo

答案 1 :(得分:2)

^(?!.*?_test\.).*\.txt$

我无法访问VS 2015 atm,但这只使用了前瞻,所以应该可以使用。

答案 2 :(得分:1)

最好的选择? Don't use regexes.特别是在像这样的简单字符串搜索案例中。

首先,根据问题的参数,可以进行几个简单的优化:

  1. 由于输入string的扩展名必须为:“。txt”,我们无需检查扩展名是否为“.txtTEMP”
  2. 唯一不匹配的条件是,输入string以“_test.txt”结尾,需要检查词干以“_test”结尾,因为扩展名已知为:“。txt “
  3. 这两项检查总是会从输入string的末尾偏移固定数量的字符。由于这两个表达式的所有信息都是已知的,因此应在编译时设置:

    constexpr auto doMatch = ".txt";
    constexpr auto doMatchSize = strlen(doMatch);
    constexpr auto doNotMatch = "_test";
    constexpr auto doNotMatchSize = strlen(doNotMatch) + doMatchSize;
    

    鉴于string input,可以按如下方式对其进行成功测试:

    if(input.size() >= doMatchSize &&
       equal(input.end() - doMatchSize, input.end(), doMatch) &&
       (input.size() < doNotMatchSize ||
       !equal(input.end() - doNotMatchSize, input.end() - doMatchSize, doNotMatch)))
    

    您可以在此处查看实时示例:http://ideone.com/7BcyFi

答案 3 :(得分:0)

模仿你真正想要的外观(但不幸的是在C ++ 11中不支持)的一个技巧是反转字符串,然后使用前瞻。你的正则表达式会变成类似

的东西
^txt\.(?!tset_).*

您尝试前瞻的问题是它应用于它应该也开始匹配'.txt'的位置。部分。所以你的正则表达式的'(?!_ test)(。txt)'部分说'我想要的东西不是以_test开头,而是匹配.txt'。以.txt结尾的任何内容实际上都与之匹配,这就是为什么它不起作用。

更新:带有负面lookbehind的正则表达式(在c ++中不起作用,但在python中起作用):

^.*(?<!_test)\.txt$