代码之家  ›  专栏  ›  技术社区  ›  Gopal Chitalia

使用正则表达式从字符串中提取文本

  •  4
  • Gopal Chitalia  · 技术社区  · 7 年前

    我有一根很大的绳子。这个字符串中有许多段落。每个段落以 标题 特殊模式。

    == Title1 == // Paragraph starts ............. ............. // Some texts ............. End of Paragraph ===Title2 === // Paragraph starts ............. ............. // Some texts .............

    标题的格式是:

    标题 以等于(=)开头,可以后跟任意数量的=。

    2.)在=之后,可以有一个空格(虽然不需要),后面跟着文本。

    3.)文本完成后,可以再次有一个空格(不需要),后跟任意数量的等于(=)。

    (4)现在段落开始。我必须提取文本,直到它遇到类似的模式。

    有人能帮我怎么处理regex吗?短暂性脑缺血发作

    4 回复  |  直到 7 年前
        1
  •  3
  •   Wiktor Stribiżew    7 年前

    你可以用

    re.findall(r'(?m)^=+[^\S\r\n]*(.*?)[^\S\r\n]*=+\s*(.*(?:\r?\n(?!=+.*?=).*)*)', s)
    

    regex demo

    细节

    • (?m)^ -线的起点
    • =+ = 字符
    • [^\S\r\n]* -除了CR和LF之外,没有或多个空白字符
    • (.*?) -第1组:除换行符以外的任何零个或多个字符,尽可能少
    • -除了CR和LF之外,没有或多个空白字符
    • =+ = 字符
    • \s*
    • (.*(?:\r?\n(?!==+.*?=).*)*) -第2组:
      • .*
      • (?:\r?\n(?!=+.*?=).*)* -零个或多个序列
        • \r?\n(?!=+.*?=) = =
        • .*

    Python demo :

    import re
    
    rx = r"(?m)^=+[^\S\r\n]*(.*?)[^\S\r\n]*=+\s*(.*(?:\r?\n(?!=+.*?=).*)*)"
    s = "== Title1 ==\n..........................\n.............\nEnd of Paragraph\n===Title2 ===\n.............\n.............\n............."
    print(re.findall(rx, s))
    

    输出:

    [('Title1', '..........................\n.............\nEnd of Paragraph'), ('Title2', '.............\n.............\n.............')]
    
        2
  •  2
  •   utks009    7 年前

    这可能有助于找到每个段落的标题和每个段落的行。

    text = """== Title1 == // Paragraph starts
    .............
    ............. // Some texts
    .............
    End of Paragraph
    ===Title2 === // Paragraph starts
    .............
    ............. // Some texts
    .............
    """
    import re
    
    reg = re.compile(r'(?:[=]+\s*\w+\s*[=]+)')
    
    for i in text.split('\n'):
        if re.search(reg, i):
            t = re.sub(r'=', '', i)
            print('Title:', t.strip())
        else:
            print('line:', i.strip())
    
     # Output like this
       Title: Title1  // Paragraph starts
       line: .............
       line: ............. // Some texts
       line: .............
       line: End of Paragraph
       Title: Title2  // Paragraph starts
       line: .............
       line: ............. // Some texts
       line: .............
       line: 
    
        3
  •  2
  •   Sushant    7 年前

    你可以试试这个-

    x = "== Title1   ==="
    ptrn = "[=]{1,}[\s]{0,}[\w]+[\s]{0,}[=]{1,}"
    if re.search(ptrn, x):
        x = x.replace('=', '').strip()
    

    会给你 Title1

    x = '== Title1   ===nansnsk fnasasklsanlkas lkaslkans \n== Title2 ==='
    titles = [i.replace('=', '').strip() for i in re.findall(ptrn, x)]
    # OP ['Title1', 'Title2']
    

    模式是-

    "^[=]{1,}[\s]{0,}[\w]+[\s]{0,}[=]{1,}"
    

    [\s]{0,}-零到无限等号之间的匹配

    [\w]+-匹配[a-zA-Z0-9_u]一次或多次

    = 具有 '' 把它从空间上剥离。你可以试试 regex101 这在测试regex时非常有用

        4
  •  1
  •   Michał Turczyn    7 年前

    1.)新段落标题以等于(=)开头,可以后跟任意数字=。

    这可以用 =+ .

    2.)在=之后,可以有一个空格(虽然不需要),后面跟着文本。

    因此标题的模式变成: =+[^=]+=+\n ,也就是说,至少匹配一个 = ,则某些文本不包括 = =

    捕捉这些模式之间的所有内容将为您提供所需的文本。

    最后,你的模式应该是: =+[^=]+=+\n([\w\W]+\n)(?==+[^=]+=+\n)

    Demo