【Python】正则
特殊字符转义
以下字符都需要用 反斜线(\)来进行特殊字符的转义。
\n - 换行符
\t - 制表符
\ - 反斜线本身
. - 点号(任意单个字符)
星号(0次或多次重复前面的元素)
加号(1次或多次重复前面的元素)
? - 问号(零次或一次重复前面的元素)
[] - 方括号内的任何字符集合
() - 分组操作符
{} - 花括号内指定数量的重复次数
起因,python正则匹配,从'你好aaa+'匹配‘aaa+’,我就想完整的匹配aaa+,但是实际效果是'你好a'这种的也能匹配上。
debug发现原来+在正则中是特殊字符。如果要匹配 + 字符本身,你需要使用反斜杠 \ 对它进行转义。即遇见 + 的pattern用 /+ 来替换,
modified_string = original_string.replace("+", "/+")
‘aaa+’被解释为:匹配前面的字符 'aaa' 一次或多次。
import re re.search('aaa+', 'a') # none re.search('aaa+', 'aaab') # re.search('aaa+', 'ab') # none re.search('aaa+', 'aab') # none re.search('aaa+', 'aaaaaab') #
re.match() 与 re.search() 的区别
1. `re.match()`:
- `re.match()` 用于从字符串的起始位置开始匹配正则表达式。
- 如果匹配成功,`re.match()` 返回一个匹配对象;如果匹配失败,它返回 `None`。
- 它只匹配字符串的第一个子串,也就是说,它不会扫描整个字符串,而是在找到第一个匹配项后停止。
re.match 尝试从字符串的起始位置匹配一个模式,如果不是起始位置匹配成功的话,match()就返回none。
2. `re.search()`:
- `re.search()` 用于在字符串中扫描正则表达式,并返回第一个匹配项。
- 如果匹配成功,`re.search()` 返回一个匹配对象;如果匹配失败,它返回 `None`。
- 它会扫描整个字符串,直到找到第一个匹配项为止。
简而言之,`re.match()` 通常用于检查字符串的起始部分是否与正则表达式匹配,而 `re.search()` 用于在整个字符串中查找匹配项。下面是一个示例,展示这两个函数的区别:
总结:search()更符合需求。
import re # 示例字符串 text = "这是一个测试字符串,包含多个部分。" # 正则表达式 pattern1 = r'测试' pattern2 = r'多个部分' # 使用re.match() match1 = re.match(pattern1, text) match2 = re.match(pattern2, text) print(f"match1: {match1}") # match1: None print(f"match2: {match2}") # match2: None # 使用re.search() search1 = re.search(pattern1, text) search2 = re.search(pattern2, text) print(f"search1: {search1}") # search1: print(f"search2: {search2}") # search2:
re.search()与 re.findall() 的区别
re.search(pattern, string, flags=0)
- re.search() 函数用于搜索字符串中是否有匹配正则表达式的部分。
- re.search() 通常用于检查一个字符串是否包含某个模式,或者找到匹配模式的第一个位置。
re.findall(pattern, string, flags=0)
- re.findall() 函数用于找到字符串中所有匹配正则表达式的部分,并返回一个列表。
- 它返回所有匹配项的列表,如果没有找到任何匹配项,则返回空列表。
- re.findall() 通常用于提取字符串中所有匹配模式的部分。
总结一下,re.search() 用于查找单个匹配项,而 re.findall() 用于查找所有匹配项。
如果你只需要找到第一个匹配项,可以使用 re.search();如果你需要找到所有匹配项,应该使用 re.findall()。
注意: match 和 search 是匹配一次 findall 匹配所有。
re.findall()
matches = re.findall(pattern, str)
re.sub()
# 将str中匹配到的pattern部分替换为'' new_str = re.sub(pattern, '', str)
re.compile()
compile2个()是什么意思?组合的意思,括号1+括号2组成一个匹配模式。
e.g. case分析
(.卖店|(官方)?旗舰店|专营店|专卖)
- . 表示任何单个字符(除了换行符)。
- 卖店、(官方)?旗舰店、专营店 或 专卖:这些是不同的选项,匹配与之相匹配的字符串。
- 括号 () 用于组匹配,() 中的表达式可以作为一个组一起被引用。
- (官方)? 表示“官方”这个词是可选的,? 表示前面的元素出现零次或一次。
pattern = re.compile("(.{0,30})(.卖店|(官方)?旗舰店|专营店|专卖)") # |是或的意思,“.卖店” or “(官方)?旗舰店” 都匹配了一次 # (.{0,30}) 是在“.卖店” or “(官方)?旗舰店”,前最多出现30个字符。 mystr = '官方旗舰店是卖店' find_all = re.findall(pattern, mystr) find_all # [('官方旗舰店', '是卖店', '')] # '这是一'???? mystr = '这是一个卖店' find_all = re.findall(pattern, mystr) find_all # [('这是一', '个卖店', '')] # “.卖店” or “专营店” 都匹配了一次 mystr = '专营店是卖店' find_all = re.findall(pattern, mystr) find_all # [('专营店', '是卖店', '')] # 不 从哪来? mystr = '专卖不是卖店' find_all = re.findall(pattern, mystr) find_all # [('专卖不', '是卖店', '')] # .是必须要匹配一个字符的 mystr = '卖店这是一个' find_all = re.findall(pattern, mystr) find_all # [] mystr = '旗舰店是卖店这不是官方' find_all = re.findall(pattern, mystr) find_all # [('旗舰店', '是卖店', '')]
case2, 其实没太理解
第一个()感觉有和没有没区别。
但是匹配的字符串,必须要以第二个括号里的词结束。
pattern = re.compile("(去|厨房卫浴|^)(.卖店|(官方)?旗舰店|专营店|专卖)") # 2个()什么意思? mystr = '去迭戈' find_all = re.findall(pattern, mystr) find_all # [] # ------------------------------------------------------------------ mystr = '去迭戈专卖' find_all = re.findall(pattern, mystr) print(f"find_all: {find_all}") print(f"re: {re.search(pattern, mystr)}") find_all: [('去', '专卖', '')] re: # ------------------------------------------------------------------ mystr = 'c去迭戈专卖' find_all = re.findall(pattern, mystr) print(f"find_all: {find_all}") print(f"re: {re.search(pattern, mystr)}") find_all: [('c去迭戈', '专卖', '')] re: # ------------------------------------------------------------------ mystr = '专卖' find_all = re.findall(pattern, mystr) print(f"find_all: {find_all}") print(f"re: {re.search(pattern, mystr)}") find_all: [('', '专卖', '')] re:
常用匹配符
模式 描述 ^ 匹配字符串开头 $ 匹配字符串结尾 . 匹配任意字符 * 匹配前面的字符零次或多次 + 匹配前面的字符一次或多次 ? 匹配前面的字符零次或一次 [] 匹配括号中列举的任意一个字符 [^] 匹配除了括号中列举的字符以外的任意一个字符 其他匹配1-n个,见python str 正则匹配两个标点符号之间的内容 python正则匹配多个数字_lanhy的技术博客_51CTO博客
^说明
^ 是一个特殊字符,它表示“匹配输入字符串的开始位置”。具体来说,当 ^ 与一个字符集或字符串前缀相结合时,它表明匹配必须从该字符集或字符串的开始处发生。
以下是一些使用 ^ 的例子:
- ^abc:匹配任何以 "abc" 开头的字符串。
- ^A:匹配任何以大写字母 'A' 开头的字符串。
- ^[a-z]:匹配任何以小写字母开头的字符串。
- ^[0-9]:匹配任何以数字开头的字符串。
需要注意的是,^ 只在正则表达式的第一个字符位置有特殊含义。如果在正则表达式中它不是第一个字符,它就仅仅是一个普通的字符,而不是表示行的开始。例如,在 a^b 中,^ 只是字符 '^' 本身,而不是特殊符号。
举例
实践1:匹配12g
pattern = r"\d+\s*[Gg][Bb]?" # 256g, 12g
实践2:匹配12g+12g, 12gb+12gb, 12g+1
pattern = r"\d+\s*[g]?[b]?\+\d+\s*[Gg]?[Bb]?"
希望匹配12g+8, 126gb+8g, 8+126等字符串。
结论
pattern1 = r"\d+\s*[g]?[b]?\+\s*\d+\s*[Gg]?[Bb]?" # '128gb+256gb', '8+256g', '8+128' matches = re.findall(pattern1, text) # list print('matches:', matches) pattern2 = r"\d+\s*[Gg][Bb]?" # 256g, 12g pattern = r"\d+\s*[mm]" # 20mm
- \d+ 匹配一系列数字。
- \s* 匹配零个或多个空格。
- \+? 匹配零个或一个加号。
- \d+ 再次匹配一系列数字。
- \s* 再次匹配零个或多个空格。
- [Gg] 匹配字母 "G" 无论大小写。
- [Bb]? 匹配零个或一个字母 "B" 无论大小写。
实践3:判断字符串时候含有list中的某个词
rule_set # 很长的一个含各种关键词的set(去重) rule_pattern = re.compile("|".join(rule_set)) find_rule = re.findall(rule_pattern, text) if find_rule: print("匹配到的关键词", find_rule[0])
实践4:匹配整数+小数
pattern = r'\d+\.?\d*' # 匹配小数 text = '今天周二5.0' digit = re.search(pattern, text) digit.group() # '5.0' text = '今天周二5' digit = re.search(pattern, text) digit.group() # '5' text = '今天1.325周二' digit = re.search(pattern, text) digit.group() # '1.325'
实践5:匹配模型中加数字
{m,n} 是一个量词,用来指定前面的元素出现的次数范围。
所以,(.{0,30}) 表示匹配任意0到30个除换行符之外的任意字符。这意味着这个表达式可以匹配一个空字符串,或者任意数量(最多30个)的任意字符。
e.g. 匹配“今日特价”,今日和特价中间最多出现0-2个字符。
pattern = re.compile("今日.{0,2}特价") text = '今日特价' re.search(pattern,text) # text = '今日你好特价' re.search(pattern,text) # text = '今日你好好特价' re.search(pattern,text) # 无
实践6:非汉字部分全部剔除*
pattern = re.compile(r'[^\u4e00-\u9fff]') # 用于匹配任何不在汉字范围内的 Unicode 字符。 text = '198301周二:' text_clear = re.sub(pattern, '', text).strip() # 是所有非汉字的字符 text_clear # '周二' text = ':你好:' text_clear = re.sub(pattern, '', text).strip() # 是所有非汉字的字符 text_clear # '你好'
还没有评论,来说两句吧...