我正在尝试从字符串中解析IP地址:
>>> import re
>>> input_str = '''
kjhdkjfh shfkjdsh shfk 1.1.1.1 kaseroi 1.1.1.1 jsoiu 1.1.1.1
1
1
11
123
132132.23213.213213.123213
23.23.23.23 2321321.33.3.3.3 3.3..3.3.3.3.3.
3.3.3.3.3.3
3.3.3.3
34.5.6.7
agdi 123213.44.4.5 12.12.12.12
'''
>>>
>>>
>>> pattern = r"\b(?:(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])\.){3}(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])\b"
>>> re.findall(pattern, input_str)
['1.1.1.1', '1.1.1.1', '1.1.1.1', '23.23.23.23', '33.3.3.3', '3.3.3.3', '3.3.3.3', '3.3.3.3', '34.5.6.7', '12.12.12.12']
>>>
但有效的IP列表是:
['1.1.1.1', '1.1.1.1', '1.1.1.1', '23.23.23.23', '3.3.3.3', '34.5.6.7', '12.12.12.12']
正则表达式有什么问题吗?
答案 0 :(得分:3)
您只需在模式中添加负向前瞻和后瞻。
(?<!\.)\b(?:(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])\.){3}(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])\b(?!\.\d?)
或强>
(?<!\S)(?:(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])\.){3}(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])(?!\S)
(?<!\S)
负面的后视断言,匹配前的(什么或字符)是任何但不是非空格字符。(?!\S)
否定前瞻声明匹配后的内容可以是任何非空格字符。代码:
>>> re.findall(r'(?<!\S)(?:(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])\.){3}(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])(?!\S)', input_str)
['1.1.1.1', '1.1.1.1', '1.1.1.1', '23.23.23.23', '3.3.3.3', '34.5.6.7', '12.12.12.12']
答案 1 :(得分:1)
您无法使用\b
来限制正则表达式,因为.
中包含\b
。从输入字符串我们可以注意到ips是使用空格分隔的,因此\s
是一个更好的选择。
使用\s
的外观更改正则表达式可以实现目的
>>> attern = r"(?<=\s)(?:(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])\.){3}(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[0-9]?[0-9])(?=\s)"
>>> re.findall(attern, input_str)
['1.1.1.1', '1.1.1.1', '1.1.1.1', '23.23.23.23', '3.3.3.3', '34.5.6.7', '12.12.12.12']