python(三) 字符串与正则表达式 1 字符串 1.1 字符串格式化 语法:'格式字符' %要格式化的内容
1 2 3 4 5 6 x = 16 print ('%o' %x)print ('%x' %x)print ('%e' %x)print ('%d, %c' %(65 , 65 )) print ('%s' %[1 , 2 , 3 ])
使用 format()方法进行格式化
1 2 3 4 5 6 7 8 9 10 11 12 13 14 print ('The number {0} in hex is: {0:#x}, the number {1:,} in oct is {1:#o}' .format (16 , 1234 ))print ('My name is {name}, my age is {age}' .format (name = 'clz' , age = 21 )) position = (1 , 2 , 3 )print ('x: {0[0]}, y:{0[1]}, z: {0[2]}' .format (position))print ('{0:.4f}' .format (1.23456 )) print ('{0:.2%}' .format (1 /3 )) print ('{0:^10.2%}' .format (1 /3 ))
从 Python 3.6.x 开始支持一种新的字符串格式化方法,官方叫做 Formatted String Literals, 简称为 f-字符串,在 Python 3.8 之后的版本中,支持 print(f’{width=}’)形式的用法++9+++
1 2 3 w = 1 h = 2 print (f'width is {w} , height is {h} ' )
1.2 字符串常用方法 **find()、rfind()、index()、rindex()、count()**:
1 2 3 4 5 6 7 8 9 10 11 12 13 s = 'apple, peach, banana, peach' print (s.find('peach' )) print (s.find('peach' , 8 )) print (s.find('peaach' , 6 , 24 )) print (s.rfind('p' )) print (s.index('p' )) print (s.index('pe' ))print (s.count('p' ))
**split()、rsplit()、partition()、rpatition()**:
1 2 3 4 5 6 7 8 9 10 11 12 13 s = 'a, b, c, d, e, hello' li = s.split(',' ) print (li) li = s.partition(',' ) print (li) li = s.rpartition(',' )print (li) s = 'hello\t\tworld I am\n\n\nclz' print (s.split())print (s.split(None , 2 ))
**join()**:效率比直接使用’+’拼接高
1 2 3 4 li = ['a' , 'b' , 'c' , 'apple' , 'True' ] sep = '::' print (sep.join(li))
**lower()、upper()、capitalize()、title()、swapcase()**:
1 2 3 4 5 6 s = 'Hello World, hello python' print (s.lower()) print (s.upper()) print (s.capitalize()) print (s.title()) print (s.swapcase())
**replace()**:
1 2 3 4 5 6 7 8 words = ('非法' , '话' , '暴力' ) text = '这句话有非法内容' for word in words: if word in text: text = text.replace(word, '**' )print (text)
maketrans()、translate()
1 2 3 4 5 table = '' .maketrans('0123456789' , '零一二三四五六七八九' ) s = '2021年10月1日' print (s.translate(table)) s = '二零二一年一零月一日' print (s.translate(table))
**strip()、rstrip()、lstrip()**:
1 2 3 4 5 6 7 8 9 10 11 12 13 s = ' hello \n' print (len (s))print (s)print (len (s.strip())) print (s.strip())print (len (s.rstrip()))print (s.rstrip()) s = 'aabbccddffee' print (s.lstrip('ab' )) print (s.lstrip('ac' ))
**eval()**:
1 2 3 4 5 print (eval ('1 + 1' )) a = 3 b = 4 print (eval ('a + b' ))
使用 eval()需要注意的问题:它可以计算任何合法表达式的值,即用户可以用特殊的字符串进行攻击
in :
使用关键字来判断一个字符串是否在另一个字符串中
1 2 print ('abc' in 'aabbcc' ) print ('abc' in 'abcabc' )
**startswith()、endswith()**:
1 2 3 4 s = "Hello World!" print (s.startswith('He' )) print (s.startswith('He' , 5 )) print (s.startswith('He' , 0 , 3 ))
其他方法:
1 2 3 4 5 6 7 8 9 10 11 12 print ('1234abcd' .isalnum())print ('1234abcd' .isalpha())print ('1234abcd' .isdigit())print ('abcd' .isalpha())print ('1234.053' .isdigit()) print ('00123400' .isdigit())print ()print ('Hello world!' .center(20 ))print ('Hello world!' .center(20 , '=' ))print ('Hello world!' .ljust(20 , '=' ))print ('Hello world!' .rjust(20 , '=' ))
1.3 字符串常量 1 2 3 4 5 6 7 8 9 10 11 12 13 import stringprint ('数字: ' , string.digits)print ('字母: ' , string.ascii_letters)print ('特殊符号: ' , string.punctuation) x = string.digits + string.ascii_letters + string.punctuationimport randomprint ('' .join([random.choice(x) for i in range (8 )])) print ('' .join(random.sample(x, 8 )))
2 正则表达式 正则表达式使用预定义的特定模式去匹配一类具有共同特征的字符串,主要用于字符串处理,可以快速、准确地完成复杂的查找、替换等处理任务。
2.1 直接使用 re 模块函数 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 import re text = 'alpha,beta,gamma,delta' print (re.split('[,]+' , text)) pat = '[a-zA-Z]+' print (re.findall(pat, text)) pat = '{name}' text = 'Dear {name}' print (re.sub(pat, 'clz' , text)) s = 'a s d' print (re.sub('a|s|d' , 'test' , s)) print (s) print (re.escape('http://www.python.org' )) print (re.match ('a|b' , 'acgs' )) print (re.match ('a|b' , 'cde' )) print (re.match ('done|quit' , 'testdone' )) print (re.search('done|quit' , 'testdone' )) text = '''good bad test clz''' print (re.findall(r'\w+' , text)) print (re.findall(r'^\w+$' , text)) print (re.findall(r'^.+$' , text, re.S)) print (re.findall(r'^.+$' , text, re.M))
2.2 使用正则表达式对象 使用正则表达式对象的用法和正常使用 re 模块基本一样,首先通过 re 模块的 compile()函数将正则表达式编译生成正则表达式对象,然后再使用正则表达式对象提供的方法进行字符串处理。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 import re example = 'ShanDong Institute of Business and Technology is a very beautiful school.' pattern = re.compile (r'\bB\w+\b' ) ''' \b表示匹配单词头或单词尾 \w表示匹配任何字母、数字以及下划线 +表示匹配位于+之前的字符或子模式的1次或多次重复 ''' print (pattern.findall(example)) pattern = re.compile (r'\w+g\b' ) print (pattern.findall(example)) pattern = re.compile (r'\b[a-zA-Z]{3}\b' ) print (pattern.findall(example)) pattern = re.compile (r'\b\w*a\w*\b' ) print (pattern.findall(example))
2.3 子模式与 Match 对象 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 import re telNumber = '''Suppose my Phone No. is 0535-1234567, yours is 010-12344567, his is 025-123456789''' pattern = re.compile (r'(\d{3,4})-(\d{7,8})' ) print (pattern.findall(telNumber)) email = 'tony@tiremove_thisger.net' m = re.search('remove_this' , email) print (email[:m.start()] + email[m.end():])''' Match对象的start()方法: 返回指定子模式内容的起始位置 Match对象的end()方法: 返回指定子模式内容的结束位置的下一个位置 ''' m = re.match (r'(\w+) (\w+)' , 'Isaac Newton, physicist' )print (m.group(0 )) print (m.group(1 )) print (m.group(2 )) print (m.group(1 , 2 )) ''' group(): 返回匹配的一个或多个子模式内容 ''' m = re.match (r'(\d+)\.(\d+)' , '12.3456' )print (m.groups())''' groups(): 返回一个包含匹配的所有子模式内容的元组 ''' m = re.match (r'(?P<first_name>\w+) (?P<last_name>\w+)' , 'Malcolm Reynolds' ) print (m.groupdict())
练习理解:使用正则表达找出 AABC 和 ABAC 类型的成员
首先,直接给出两个做法的答案
做法 1 :
1 2 3 pattern = r'((.).\2.|(.)\3..)' for item in findall(pattern, text): print (item[0 ])
做法 2 :
1 2 3 pattern = r'(\b(?P<F>\w)\w(?P=F)\w\b|\b(?P<D>\w)(?P=D)\w\w\b)' for item in findall(pattern, text): print (item[0 ])
做法 1 讲解:
首先,有一个会用到的重要概念,使用括号表示一个子模式
先 ABAC 类型(实际上 ABAB 也能匹配到,书上的也是这样,将错就错了,简单点),小数点表示能匹配到除换行符的任意单个字符,所以先构建
正则表达式 pattern = r'(..)'
第三个应该要和第一个相同,所以不能直接pattern = r'(...)'
, 这个时候就要用上正则表达式的复制粘贴功能了,首先,做好复制工作–用括号把要复制的部分包住 , pattern = r'((.).)'
, 然后是粘贴工作–反斜线加要粘贴的内容是第几个子模式, pattern = r'((.).\2)'
,这里是 2 的原因就是上面说的重点了,使用括号表示一个子模式 ,我们要把第二个括号里的东西复制粘贴,所以自然就是 2 了
第四个随便,所以正则表达式变成 pattern = r'((.).\2.)'
再 AABC 类型的,先加上’|’,pattern = r'((.).\2.|)'
,这里的|左右不能有空格
之后的原理和上面的相同,需要注意的是:括号并不会重置为 0,才开始算,而是前面的括号也算 ,所以变成 pattern = r'((.).\2.|(.)\3..)'
之后通过循环即可得到结果,因为 findall()是找出所有的匹配项,所以只需要 item[0]就行了
做法 2 讲解:
首先原理和做法 1 一样,不同的是复制粘贴的形式,做法 2 是先通过 (?P=<groupname>)
给要复制的内容命名,然后通过 (?P=groupname)
把内容粘贴过去