19

我有一个源文件,其中包含数百个字符串flecha.jpgflecha1.jpg,但我需要找到任何其他.jpg图像的出现(即casa.jpg,,moto.jpg等等)

我尝试过使用带有否定后视的正则表达式,如下所示:

(?<!flecha|flecha1).jpg

但它不起作用!Notepad++ 只是说它是一个无效的正则表达式。

我在其他地方尝试过正则表达式并且它有效,这是一个示例,所以我猜这是 NPP 处理正则表达式或lookbehinds/lookaheads 语法的问题。

那么我怎样才能在 NPP 中实现相同的正则表达式结果呢?

如果有用,我使用的是 Notepad++ 6.3 Unicode

作为一个额外的,如果你这么好,实现同样的事情的语法是什么,但可选的数字(在这种情况下只有'1')作为我的字符串的后缀?(即使它在 NPP 中不起作用,只是要知道)......

我试过(?<!flecha[1]?).jpg了,但它不起作用。它应该与其他正则表达式一样工作,请参见此处(RegExr

4

3 回答 3

18

Notepad++ 似乎没有实现可变长度的look-behinds(某些工具会发生这种情况)。一种解决方法是使用多个固定长度的后视:

(?<!flecha)(?<!flecha1)\.jpg

如您所见,匹配项是相同的。但这适用于 npp。

请注意,我转义了.,因为您正在尝试匹配扩展名,所以您想要的是文字.. 你有的方式,它是一个通配符 - 可以是任何字符。

关于额外的问题,不幸的是,因为我们不能有可变长度的后视,所以如果没有多个后视,就不可能有可选的后缀(数字)。

于 2013-06-25T01:08:40.127 回答
15

解决 Notepad++ 中可变长度负后向限制的问题

这里给出了几种在 Notepad++(或任何具有相同限制的正则表达式引擎)中解决此限制的策略

定义问题

Notepad++ 不支持使用可变长度的否定后向断言,如果有一些变通方法会很好。让我们考虑原始问题中的示例,但假设我们希望避免出现在之后flecha任意位数命名的文件flecha,以及在 之前以任何字符命名的文件flecha。在这种情况下,使用可变长度负后向的正则表达式看起来像(?<!flecha[0-9]*)\.jpg.

在这个例子中我们不想匹配的字符串

  • flecha.jpg
  • flecha1.jpg
  • flecha00501275696.jpg
  • aflecha.jpg
  • img_flecha9.jpg
  • abcflecha556677.jpg

策略

  1. 插入临时标记

    首先对您想要避免使用的实例执行查找和替换 - 在我们的例子中是flecha[0-9]*\.jpg. 插入一个特殊的标记以形成一个不会出现在其他任何地方的图案。.对于这个例子,我们将在前面插入一个额外的.jpg,假设它..jpg没有出现在其他地方。所以我们这样做:

    寻找:(flecha[0-9]*)(\.jpg)

    用。。。来代替:$1.$2

    .jpg现在您可以使用简单的正则表达式搜索您的文档以查找所有其他文件名,例如\w+\.jpgor(?<!\.)\.jpg并使用它们做您想做的事情。完成后,执行最终的查找和替换操作,将所有实例替换为..jpg,.jpg以删除临时标记。

  2. 使用否定的前瞻断言

    否定的前瞻断言可用于确保您不匹配不需要的文件名:

    (?<!\S)(?!\S*flecha\d*\.jpg)\S+\.jpg

    分解它:

    • (?<!\S)通过断言您的匹配项前面没有非空白字符,确保您的匹配项从文件名的开头而不是中间开始。
    • (?!\S*flecha\d*\.jpg)确保匹配的内容不包含我们想要避免的模式
    • \S+\.jpg是实际匹配的内容——一串非空白字符,后跟.jpg.
  3. 使用多个固定长度的负后视

    对于您不想匹配的模式具有少量可能的长度的情况,这是一种快速(但不那么优雅)的解决方案。

    例如,如果我们知道flecha后面最多只有三位数字,我们的正则表达式可能是:

    (?<!flecha)(?<!flecha[0-9])(?<!flecha[0-9][0-9])(?<!flecha[0-9][0-9][0-9])\.jpg

于 2018-02-11T02:39:50.473 回答
2

您是否知道您只是匹配(在消费的意义上)扩展名(.jpg)?我想你想匹配整个文件名,不是吗?使用前瞻更容易做到这一点:

\b(?!flecha1?\b)\w+\.jpg

第一个\b将匹配锚定到名称的开头(假设它确实是我们正在查看的文件名)。然后(?!flecha1?\b)断言名称不是flechaor flecha1。完成后,\w+继续使用名称。然后\.jpg抓住延长线结束比赛。

于 2013-06-25T04:53:39.983 回答