不区分大小写的正则表达式,无需重新编译?


331

在Python中,我可以使用re.compile以下命令将正则表达式编译为不区分大小写:

>>> s = 'TeSt'
>>> casesensitive = re.compile('test')
>>> ignorecase = re.compile('test', re.IGNORECASE)
>>> 
>>> print casesensitive.match(s)
None
>>> print ignorecase.match(s)
<_sre.SRE_Match object at 0x02F0B608>

有没有办法做同样的事情,但是不用re.compile。在文档中找不到Perl的i后缀(例如m/test/i)。


1
您可以在以下网址
2Obe

Answers:


562

传递re.IGNORECASEflags的PARAM searchmatchsub

re.search('test', 'TeSt', re.IGNORECASE)
re.match('test', 'TeSt', re.IGNORECASE)
re.sub('test', 'xxxx', 'Testing', flags=re.IGNORECASE)

2
re.match('test', 'TeSt', re.IGNORECASE)TypeError当任一属性为时,可能会导致None。使用try & except捕捉TypeError由first_string == second_string匹配。示例代码 def equal_ignore_case(first_string, second_string): try: return re.match(first_string, second_string, re.IGNORECASE) is not None except (AttributeError, TypeError): return first_string == second_string 演示代码
Abhijeet

3
@Abhijeet在这种情况下,您真的不应该使用try / except。只需检查是否有任何字符串None在前。
erb

使用命名参数是很重要flagsre.sub,否则它传递re.IGNORECASEcount参数(S还。stackoverflow.com/questions/42581/...
L3n95

101

您还可以使用不带IGNORECASE标志(已在Python 2.7.3中进行测试)的搜索/匹配来执行不区分大小写的搜索:

re.search(r'(?i)test', 'TeSt').group()    ## returns 'TeSt'
re.match(r'(?i)test', 'TeSt').group()     ## returns 'TeSt'

2
该文档没有提到在任何特定版本中添加的功能(相对于说它(?(condition)yes|no)在2.4中添加的功能),因此我希望自re模块的第一个版本以来,该功能始终可用。在1.5中。从根本上讲,从涉及Python的所有意图和目的开始。在本页面的第一部分中途已记录了该文档:docs.python.org/2/library/re.html#regular-expression-syntax
ArtOfWarfare 2015年

4
在这里-我仔细阅读了1.5的文档,发现它记录了本页面大约60%的内容:docs.python.org/release/1.5/lib/…我还检查了1.4文档,但没有提及此功能。所以我想它是在1.5中添加的,当时regex不赞成使用该模块,而推荐使用该re模块。
ArtOfWarfare 2015年

3
这是一个很好的解决方案,因为它不需要标志。就我而言,我将搜索字符串存储在Redis中,这真的很有帮助。
私人

3
@Private:从概念上讲,它确实在整个正则表达式上设置了re.I标志,而不仅仅是它前面的捕获组。请注意,这re.match(r'''A ((?i)B) C''', "a b c").group(0)会导致对所有内容(A和C)(而不只是对B)的大小写不敏感!如果只希望特定捕获组上的大小写匹配,则这不是您要查找的机器人。
smci

1
@私人:完全可以。我的观点是在概念上与设置标志相同。在整个正则表达式上。甚至它之前的组(!)。没有语法可以说“仅在以下捕获组上不区分大小写”。
smci

53

不区分大小写的标记(?i)可以直接合并到regex模式中:

>>> import re
>>> s = 'This is one Test, another TEST, and another test.'
>>> re.findall('(?i)test', s)
['Test', 'TEST', 'test']

2
更好的选择,使正则表达式可跨平台移植,并且声明时明确表明了意图
Sina Madani

1
这种'(?i)'方法还具有可以创建一个正则表达式列表的优点,其中有些不区分大小写,有些则不区分大小写。(当然,您也可以根据需要映射re.compile该列表。)
not-just-yeti

@SinaMadani我很困惑。那比它更便携flags=re.IGNORECASE
罗曼·文森特

10

您还可以在模式编译期间定义不区分大小写的代码:

pattern = re.compile('FIle:/+(.*)', re.IGNORECASE)

5
在问题中,OP使用此方法,并询问是否还有另一种方法。
彼得·伍德

6
对于快速滚动的用户很有帮助。
Stevek '16

6

进口中

import re

在运行时处理中:

RE_TEST = r'test'
if re.match(RE_TEST, 'TeSt', re.IGNORECASE):

应当指出,不使用re.compile是浪费。每次调用上述match方法时,都会编译正则表达式。这在其他编程语言中也是错误的做法。下面是更好的做法。

在应用程序初始化中:

self.RE_TEST = re.compile('test', re.IGNORECASE)

在运行时处理中:

if self.RE_TEST.match('TeSt'):

1
谢谢!没有人谈论编译,但这是最明智的选择!
StefanJCollier

2
OP确实要求使用使用的解决方案re.compile()....
wpercy

4
#'re.IGNORECASE' for case insensitive results short form re.I
#'re.match' returns the first match located from the start of the string. 
#'re.search' returns location of the where the match is found 
#'re.compile' creates a regex object that can be used for multiple matches

 >>> s = r'TeSt'   
 >>> print (re.match(s, r'test123', re.I))
 <_sre.SRE_Match object; span=(0, 4), match='test'>
 # OR
 >>> pattern = re.compile(s, re.I)
 >>> print(pattern.match(r'test123'))
 <_sre.SRE_Match object; span=(0, 4), match='test'>

4

要执行不区分大小写的操作,请提供re.IGNORECASE

>>> import re
>>> test = 'UPPER TEXT, lower text, Mixed Text'
>>> re.findall('text', test, flags=re.IGNORECASE)
['TEXT', 'text', 'Text']

如果我们要替换与大小写匹配的文本...

>>> def matchcase(word):
        def replace(m):
            text = m.group()
            if text.isupper():
                return word.upper()
            elif text.islower():
                return word.lower()
            elif text[0].isupper():
                return word.capitalize()
            else:
                return word
        return replace

>>> re.sub('text', matchcase('word'), test, flags=re.IGNORECASE)
'UPPER WORD, lower word, Mixed Word'

1

如果您想替换但仍保留以前str的样式。有可能的。

例如:高亮显示字符串“ test asdasd TEST asd tEst asdasd”。

sentence = "test asdasd TEST asd tEst asdasd"
result = re.sub(
  '(test)', 
  r'<b>\1</b>',  # \1 here indicates first matching group.
  sentence, 
  flags=re.IGNORECASE)

测试 asdasd TEST ASD 测试 asdasd


0

对于不区分大小写的正则表达式(Regex):通过两种方式添加代码:

  1. flags=re.IGNORECASE

    Regx3GList = re.search("(WCDMA:)((\d*)(,?))*", txt, **re.IGNORECASE**)
  2. 不区分大小写的标记 (?i)

    Regx3GList = re.search("**(?i)**(WCDMA:)((\d*)(,?))*", txt)
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.