正则表达式排除特定字符

时间:2019-06-12 20:43:30

标签: regex

我有一个正则表达式公式,可用于查找数据中的特定模式。具体来说,它从查找“ {}”括号之间的字符开始,然后查找“ p。”并在其后获取数字。我注意到,在某些情况下,如果括号后不久没有“ p。”值,它将继续通过下一个括号并在其后获取数字。

例如,这是我的示例数据:

{Hello}, [1234] (Test). This is sample data used to answer a question {Hello2} [Ch.8 p. 87 gives more information about...

这是我的代码:

\{(.*?)\}(.*?)p\. ([0-9]+)

我希望它仅返回此值:

{Hello2}  [Ch.8 p. 87

但是它返回此:

{Hello},  [123:456] (Test).  This is stample data used to answer a
question {Hello2}  [Ch.8 p. 87

是否可以排除包含“ {”的字符串?

4 个答案:

答案 0 :(得分:6)

您的模式首先从{到}进行匹配,然后以非贪婪的方式.*?进行匹配,放弃匹配,直到它可以匹配p,点号和1+个数字。

之所以可以这样做,是因为该点也可以匹配{}

您可以使用否定的字符类[^{}]来匹配{}

\{[^{}]*\}[^{}]+p\. [0-9]+

Regex demo

答案 1 :(得分:0)

您的表达式似乎运行良好,我想我们只希望捕获所需的输出,而不捕获其他输出,可以通过对原始表达式进行一些修改来实现:

(?:[\s\S]*)(\{(.*?)\}(.*?)p\. [0-9]+)

Demo 1

或以下表达式:

(?:[\s\S]*)(\{.*)

Demo 2

RegEx电路

jex.im可视化正则表达式:

enter image description here

测试

const regex = /(?:[\s\S]*)(\{.*)/gm;
const str = `{Hello},  [123:456] (Test).  This is stample data used to answer a
question {Hello2}  [Ch.8 p. 87`;
let m;

while ((m = regex.exec(str)) !== null) {
    // This is necessary to avoid infinite loops with zero-width matches
    if (m.index === regex.lastIndex) {
        regex.lastIndex++;
    }
    
    // The result can be accessed through the `m`-variable.
    m.forEach((match, groupIndex) => {
        console.log(`Found match, group ${groupIndex}: ${match}`);
    });
}

答案 2 :(得分:0)

这是您在Java中的操作方式。正则表达式应该相当通用。

      String test = "{Hello2} [Ch.8 p. 87 gives more information about..";
      String pat = "(\\{.*?\\}.*p.*?\\d+)";
      Matcher m = Pattern.compile(pat).matcher(test);
      if (m.find()) {
         System.out.println(m.group(1));
      }

如果您对数据的了解更多,则可以提供更具体的信息。例如,每个{}信息是否都在单独的一行上开始?数据是什么样子,您想忽略什么?

答案 3 :(得分:0)

根据示例文本,您可以稍微简化正则表达式,并避免在匹配页码之前匹配第二个打开的花括号(除非捕获组有其他用途)。例如:

{[^{]*p\.\s\d+
  • {匹配一个大括号
  • [^{]*匹配以下所有字符,除了另一个大括号
  • p\.\s\d+匹配“ p”,后跟句点,空格和一个或多个数字