【问题标题】:Why is regex not returning any matches?为什么正则表达式不返回任何匹配项?
【发布时间】:2021-12-27 16:22:54
【问题描述】:

我正在尝试使用正则表达式从 Outlook 电子邮件正文中的文本中提取某些子字符串。

这是我正在尝试使用的带有正则表达式的函数:

def EventDescription(emailbody):
    regex = r'\d\d:\d\d\sDescription: (.*?)\s(?:_)'
    substring = re.findall(regex, emailbody, re.DOTALL)
    # return the matches
    return substring

这是我尝试对其执行正则表达式的原始字符串:

***External Sender - This email is from an external sender.*** 
     
Date/Time Start:     
2021-12-25 08:38     
Anticipated Date/Time Restored:  
2021-12-25 16:21     
Duration:    
7.72     
Outage Type:     
Forced Outage (FO)   
Capacity De-Rate:    
0.00     
Maximo Work Orders:  
Work Order #:NA00360131, Description: ALO1: ALO1_B002_P008.Inv016 - Inverter 16 is derating due to a broken tracking motor.  

Created On: 2021-12-26 09:06
Description: Updated!
Inverter 16 is restored by site tech.
________________________________________

     
Date/Time Start:     
2021-12-25 09:53     
Anticipated Date/Time Restored:  
2021-12-27 16:00     
Duration:    
54.12    
Outage Type:     
Forced Outage (FO)   
Capacity De-Rate:    
0.85     
Maximo Work Orders:  
Work Order #:NA00360131, Description: ALO1: ALO1_B002_P008.Inv016 - Inverter 16 is derating due to a broken tracking motor.  

Created On: 2021-12-25 13:58
Description: 
Updated ETR.
________________________________________

     
Date/Time Start:     
2021-12-25 09:53     
Anticipated Date/Time Restored:  
2021-12-25 16:00     
Duration:    
6.12     
Outage Type:     
Forced Outage (FO)   
Capacity De-Rate:    
0.85     
Maximo Work Orders:  
Work Order #:NA00360131, Description: ALO1: ALO1_B002_P008.Inv016 - Inverter 16 is derating due to a broken tracking motor.  

Created On: 2021-12-25 09:54
Description: 
Inverter 16 tripped offline. No fault code available in FleetCon or SCADA. Site personnel informed.
________________________________________

但是当我尝试从列表“子字符串”中提取其中一个条目时,我收到“IndexError: list index out of range”错误。有什么建议吗?

【问题讨论】:

  • 您的模式不匹配,因为在示例文本中没有匹配 \s_
  • 你能把文本文字放在代码块中吗(没有语法高亮,又名``` text)?我觉得问题源中的下划线分隔符是文本的一部分。然而它们目前由降价引擎解析,让我们感觉您正在尝试解析 3 个单独的字符串而不是 1 个大字符串。
  • 我相信我已经修复了我的原始帖子以更好地显示原始字符串(如果不是,请告诉我)但你是正确的。当我将电子邮件正文复制/粘贴到文本编辑器中时,分隔符显示为下划线,这就是为什么我将它们作为原始正则表达式的一部分包含在内,以区分我尝试匹配的 3 个单独实例。
  • @RandomUser27 您的模式似乎有效吗?见ideone.com/hgCRDP

标签: python regex


【解决方案1】:

您的正则表达式非常复杂,不会返回任何匹配项。你应该试试这个:

regex = r'\d\d:\d\d\sDescription: (.*)'

它只是匹配Description: 之后的整个字符串。使用您的示例字符串,它会返回您请求的所有匹配项。

编辑:您还必须从findall 中删除一个参数才能使其工作。 re.DOTALL 不会在新行处停止匹配。使用以下代码,您应该会收到所需的输出:

def EventDescription(emailbody):
    regex = r'\d\d:\d\d\sDescription: (.*)'
    substring = re.findall(regex, emailbody)
    # return the matches
    return substring

【讨论】:

  • 感谢您的回复。上面建议的问题是我需要它只返回“描述:”之后的字符串,直到“日期/时间开始:”文本之前的下一个分隔符。它应该在示例字符串中返回 3 个匹配项,因为有 3 个以时间戳开头的“描述”文本实例。当我将电子邮件正文复制到文本编辑器中时,分隔符显示为下划线,这就是为什么我的原始正则表达式末尾有 '(?:_)'。
  • 你是对的。我只测试了正则表达式而不是你的代码。您使用了一个不必要的标志。删除它会产生您想要的输出。我在答案中添加了新功能。
  • 我编辑了我的原始帖子以更好地显示原始字符串,但删除 DOTALL 的问题是在某些情况下我试图返回的子字符串跨越多行。例如,第一个匹配项应包括“更新!”以及“逆变器 16 已由现场技术恢复”。在下一行。
【解决方案2】:

试试这样的:

Description:\s(.*?)_{40,}

这样,我们将匹配描述和下划线行之间的所有内容。请注意,您仍然需要使用 DOTALL 模式。

https://regex101.com/r/qoiSwl/1

我添加了End of Event \n\n\n 只是为了突出显示每场比赛的开始和结束位置,因为换行符很难分辨。

【讨论】:

    【解决方案3】:

    使用

    \d{2}:\d{2}\s+Description:\s*(.*?)\s+_
    

    regex proof

    解释

    --------------------------------------------------------------------------------
      \d{2}                    digits (0-9) (2 times)
    --------------------------------------------------------------------------------
      :                        ':'
    --------------------------------------------------------------------------------
      \d{2}                    digits (0-9) (2 times)
    --------------------------------------------------------------------------------
      \s+                      whitespace (\n, \r, \t, \f, and " ") (1 or
                               more times (matching the most amount
                               possible))
    --------------------------------------------------------------------------------
      Description:             'Description:'
    --------------------------------------------------------------------------------
      \s*                      whitespace (\n, \r, \t, \f, and " ") (0 or
                               more times (matching the most amount
                               possible))
    --------------------------------------------------------------------------------
      (                        group and capture to \1:
    --------------------------------------------------------------------------------
        .*?                      any character (0 or more times
                                 (matching the least amount possible))
    --------------------------------------------------------------------------------
      )                        end of \1
    --------------------------------------------------------------------------------
      \s+                      whitespace (\n, \r, \t, \f, and " ") (1 or
                               more times (matching the most amount
                               possible))
    --------------------------------------------------------------------------------
      _                        '_'
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-08-09
      • 2012-10-07
      • 1970-01-01
      • 2022-01-04
      相关资源
      最近更新 更多