今天的文章是我们Python基础内容的最后一章,今天我们要讲的是正则表达式,在今天的作业后面我还会附加一组练习题,大家可以练练手看自己Python知识牢不牢固
一.正则概念
我们来思考几个问题:
其实这个问题我们在之前就解决过,我们用的是字符串的判断方法,我们今天讲的是正则表达式,那什么是正则表达式呢?
正则表达式:
作用:匹配字符(非常强大) 可以匹配任何字符
我们怎么用正则表达式实现上面的要求呢,请看我的代码:
import re
number = input('请输入手机号:')
if number.isdigit() and number[0:2] == '13' and len(number) == 11:
print(f'{number}是一个手机号')
else:
print(f'{number}不是手机号!')
a = re.findall(r'^13\d{9}$',number)
二.元字符
'''
. :匹配任何字符
\ :取消转义 内容中 \\ 表示 \
^ :限制开头 匹配字符串开头是什么内容
$ :限制结尾 匹配字符串结尾是什么内容
{}:匹配次数
{n} 必须匹配n(个)次 字符串存在n次才匹配
{n,m} 最多匹配m次 做少n次
{n,} 最少n次
{,m} 最多m次
* :0次或多次
+ :一次或多次
? :0次或1次 (限制匹配次数)
[]: 字符集合 自定义匹配项 如:a-zA-Z0-9 大小写数字
():分组匹配
import re
st = '123abdABC'
a = re.findall(r'([0-9]*),([a-zA-Z]*)',st)
print(a) # [('123','abcABC'),('','')]
| :或运算 分支条件
\d 匹配数字
\D 非数字
\w 匹配字符(英文,数字,下划线,汉字等)
\W 匹配非字符(转义符,@,中文符号等)
\s 匹配空格,制表符,换行符
\S 不匹配空格,制表符,换行符
\. 匹配.
贪婪模式
会尽可能的匹配出合适字符
<.*>
取消:
<.*?>
'''
三.re模块
我们来思考一个问题:
我为大家列出了常用的正则表达式:
'''
compile 提前编译
abc = re.compile(r'\d{5}')
st = '123456789'
a = findall(st)
findall 查找待匹配字符串里面所有符合正则表达式的字符
sub 字符串替换
st = '123456789'
a = re.sub('345','987',st,n) n表示切割次数 多了无所谓
split 字符串切割
st = '123456789'
a = re.split('3|6',st)
match 匹配开头
span() 表示匹配到内容的下标 match 表示匹配到的内容
a.span() 查看下标
a.group() 查看内容
search 匹配整个字符串 但只匹配一次
a = re.search('is',s)
a.span() 查看下标
a.group() 查看内容
'''
四.本节课内容总结
其实正则表达式不难,要记忆的东西不是很多,主要是在爬虫的方向应用的很广泛,大家多练练就能掌握.
五.两次作业答案(仅供参考,并非标准答案)
1.测试列表推导式和不用列表推导式哪一种速度快
'''测试列表推导和不用列表推导那一种速度更快
思路:
计算速度:需要用到时间
计算时间:结束时间-起始时间=运行时间
定义类:利用上下文协议
'''
# 普通方法
import time
start_time1 = time.time()
li1 = []
for i in range(10000):
li1.append(i)
end_time1 = time.time()
run_time1 = end_time1-start_time1
print(run_time1)
start_time2 =time.time()
li2 = [i for i in range(10000)]
end_time2 = time.time()
run_time2 = end_time2-start_time2
print(run_time2)
# 利用上下文协议
class Runtime:
def __enter__(self):
self.start_time = time.time()
def __exit__(self,exc_ty,exc_val,_exc_tb):
self.end_time = time.time()
self.run_time = self.end_time-self.start_time
print(f'代码运行时间为{self.run_time}')
with Runtime():
li1 = []
for i in range(50000):
li1.append(i)
with Runtime():
li2 = [i for i in range(50000)]
2.range不可以使用小数做步长,实现一个可迭代对象,可以实现小数步长
from decimal import Decimal #部分导入 高精度模块 消除浮点类型计算不准确
class FloatRange:
def __init__(self,start,end=None,step=1):
if not isinstance(start,(int,float)): #当传入一个参数时
raise TypeError
elif not isinstance(end,(int,float)) and end != None: #传入两个参数时
raise TypeError
elif not isinstance(step,(int,float)): #传入参数参数时
raise TypeError
elif end != None and end < start: #注意逻辑短路 end值的特性
print('结束值不能小于起始值')
elif step <=0: #步长值的特性
print('步长不能小于等于0')
else:
if end == None:
self.start = 0
self.end = start
self.step = step
else: #当传入参数大于等于两个时
self.start = start
self.end = end
self.step = step
def __iter__(self):
return self
def __next__(self):
self.index = self.start
if self.start>=self.end:
raise StopIteration
self.start = Decimal(str(self.start))+Decimal(str(self.step))
return self.index
for i in FloatRange(1,10,0.8):
print(i)
3.利用装饰器,记录函数的运行日志(如:保存传入参数,运行次数,返回结果,运行时间等信息)
'''
利用装饰器,记录函数的运行日志(如:保存传入参数,运行次数,
返回结果,运行时间等信息)
思路:
确定函数直接的调用关系
保存运行时间
因为首次运算代码时 相当于运行了 test = funa(test) funa函数内容全部被调用
利用特点 创建变量 保存函数运算次数
搞清函数调用过程 确定参数传入的位置(传给谁)
获取传入参数
与上同理 获取返回值
'''
import time
def funa(f):
n = [0]
def funb(a):
n[0] += 1
print(f'函数运行次数为{n[0]}')
print(f'函数传入的参数为{a}')
b = f(a)
print(f'函数返回的结果是{b}')
print(time.time())
return funb
@funa
def test(a):
print(111)
return 123
test(a=10086)
4.打开一个只读文件,如果文件不存在,则去创建这个文件
'''
打开一个只读文件,如果文件不存在,则去创建这个文件
思路:
文件不存在,就相当于open('test.txt','r')这段代码报错
则去创建这个文件
就是说↑读取文件不存在时 处理异常 创建文件
'''
try:
a = open('test.txt','r')
print(a.read())
except:
b = open('test.txt','w')
b.write('====文件已被创建====')
b.close()
六.作业和阶段性测试
本套试题共分为单选题(28分),填空题(24分),判断题(8分)编程题(40分)四部分构成,满分为100分.
至此,我们的一步步学习Python到此完结,我们接下来就要开始学习数据库了,持续关注给你带来更多优质内容!!!