簡體   English   中英

python 正則表達式如何捕獲所有可能是可選的組?

[英]python regex how to capture all groups that may be optional?

minutes_pattern = re.compile(
    r"""
(?:(?P<hours>\d+)H)?
(?:(?P<minutes>\d+)M)?
(?:(?P<seconds>\d+)S)?
""",
    re.VERBOSE,
)

我試圖捕捉所有的小時、分鍾、秒。 但是,這些可能存在也可能不存在: 示例:

PT30H20M10S
PT20M10S
PT20M
PT3010S
PT30H

我在想(?:(?P<hours>\d+)H)? 說:

  1. ?: 非捕獲組
  2. ?P 小時組名稱
  3. \d+ 任意位數
  4. H 必須存在
  5. )? 該組可能存在也可能不存在

但是這個編譯沒有捕獲任何 3 個組。 請幫忙

regex = minutes_pattern.search(duration)
print(regex.groups())

這只返回無

(None, None, None)

理想情況下,這將顯示(對於第一個示例):

group hours: 30
group minutes: 20
group seconds: 10

對於第二個示例:

group hours: None
group minutes: 20
group seconds: 10

問題是您的正則表達式成功匹配一個空字符串,因此當您使用.search搜索第一個匹配項時,第一個匹配項出現在索引 0 處,長度為 0:

>>> minutes_pattern.search(duration)
<_sre.SRE_Match object; span=(0, 0), match=''>

解決此問題的最簡單方法是在正則表達式的開頭包含字母PT ,因為這些字母始終存在於您的輸入字符串中,並且它們防止正則表達式返回空匹配:

>>> minutes_pattern = re.compile(r"PT(?:(\d+)H)?(?:(\d+)M)?(?:(\d+)S)?")
>>> minutes_pattern.search(duration)
<_sre.SRE_Match object; span=(0, 11), match='PT30H20M10S'>
>>> minutes_pattern.search(duration).groups()
('30', '20', '10')

或者,如果您不想在您的正則表達式中包含PT (也許其他一些輸入不會包含該前綴),您可以使用.findall而不是.search ,然后過濾列表以查找“非平凡”匹配:

>>> minutes_pattern = re.compile(r"(?:(\d+)H)?(?:(\d+)M)?(?:(\d+)S)?")
>>> minutes_pattern.findall(duration)
[('', '', ''), ('', '', ''), ('30', '20', '10'), ('', '', '')]
>>> next(filter(any, minutes_pattern.findall(duration)), None)
('30', '20', '10')

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM