Python内置模块(re模块、collections模块、time模块、datetime模块)

Python内置模块(re模块、collections模块、time模块、datetime模块)

  • 正则表达式小练习
  • 取消转义
  • re模块
  • re模块其他方法
  • 正则实战案例
  • collections模块
  • time模块
  • datetime模块

 

一、正则表达式小练习

# 以数字1-9开头,中间13位或16位数字,以数字0-9或小写字母x结尾
^[1-9]\d{13,16}[0-9x]$
# 以数字1-9开头,14位数字,把两位数字和0-9x组成一个组,匹配一次或者不匹配
^[1-9]\d{14}(\d{2}[0-9x])?$
# 以数字1-9开头,中间16位数字,以数字0-9或小写字母想结尾或者以数字1-9开头,后面14位数字
^([1-9]\d{16}[0-9x]|[1-9]\d{14})$

 

二、取消转义

  在原生的正则表达式中取消转义推荐使用\(每个\只能取消一个字符的转义)

  在Python中取消转义推荐使用r'\n\a\t'(也可以使用\)

 

三、re模块

  在Python中要想使用正则必须借助于模块,re就是其中之一

  1. 基本操作方法

    1)re.findall()

import re

re.findall('正则表达式', '待匹配的文本')  # 根据正则匹配除所有符合条件的数据
res = re.findall('a', 'eva jason jackson')
print(res)  # ['a', 'a', 'a']  结果是一个列表(要么有元素 要么空列表)

    2)re.search()

import re

res = re.search('正则表达式', '待匹配的文本')  # 根据正则匹配到一个符合条件的就结束
res = re.search('a', 'eva jason jackson')
print(res)  # 结果对象
print(res.group())  # 正则的结果
if res:
    print(res.group())
else:
    print('不好意思 没有找到')

      如果没有符合条件的数据,那么search返回None,并且使用group会直接报错

    3)re.match()

import re

res = re.match('a', 'bac')  # 根据正则从头开始匹配(文本内容必须在开头匹配上)
print(res)if res:
    print(res.group())
else:
    print('不好意思 没有找到')

      如果没有符合条件的数据 那么match返回None 并且使用group会直接报错

    4)re.match与re.search的区别

      re.match只匹配字符串的开始,如果字符串开始不符合正则表达式,则匹配失败,函数返回None;而re.search匹配整个字符串,直到找到一个匹配。

 

四、re模块其他方法

  1. re.split()

    split 方法按照能够匹配的子串将字符串分割后返回列表

import re

# 先按'a'分割得到''和'bcd',在对''和'bcd'分别按'b'分割
res = re.split('[ab]', 'abcd')  # 不一样的地方:中括号里有几个就切几次
print(res)  # ['', '', 'cd']

   2. re.sub()

    类似于字符串类型的replace方法

import re

res = re.sub('\d', 'H', 'eva3jason4yuan4', 1)  # 替换正则匹配到的内容
print(res)
res = re.sub('\d', 'H', 'eva3jason4yuan4')  # 不写默认替换所有
print(res)

  3. re.subn()

    返回元组,并提示替换了几处

import re

res = re.subn('\d','H', 'eva3jason4yuan4', 1)
print(res)  # ('evaHjason4yuan4', 1)
res = re.subn('\d', 'H', 'eva3jason4yuan4')
print(res)  # ('evaHjasonHyuanH', 3)

  4. re.compile()(常用)

    compile 函数用于编译正则表达式,生成一个正则表达式( Pattern )对象,供 match() 和 search() 这两个函数使用。

import re

regexp_obj = re.compile('\d+')
res = regexp_obj.search('absd213j1hjj213jk')
res1 = regexp_obj.match('123hhkj2h1j3123')
res2 = regexp_obj.findall('1213k1j2jhj21j3123hh')
print(res)
print(res1)
print(res2)

  5. re.finditer()(常用)

    和 findall 类似,在字符串中找到正则表达式所匹配的所有子串,并把它们作为一个迭代器返回。

import re

res = re.finditer('\d+','ashdklah21h23kj12jk3klj112312121kl131')
print([i.group() for i in res])

   6. 分组

import re

res = re.search('^[1-9](\d{14})(\d{2}[0-9x])?$', '110105199812067023')
print(res)
print(res.group())  # 110105199812067023
print(res.group(1))  # 10105199812067
print(res.group(2))  # 023

 

   7. 分组优先

    findall针对分组优先展示(无名分组)

import re

res = re.findall("^[1-9]\d{14}(\d{2}[0-9x])?$", '110105199812067023')
print(res)  # ['023']

    取消分组优先展示(无名分组)

import re

res1 = re.findall("^[1-9](?:\d{14})(?:\d{2}[0-9x])?$", '110105199812067023')
print(res1)

  8. 有名分组

import re

res = re.search('^[1-9](?P<xxx>\d{14})(?P<ooo>\d{2}[0-9x])?$', '110105199812067023')
print(res)
print(res.group())  # 110105199812067023
print(res.group(1))  # 10105199812067  无名分组的取值方式(索引取)
print(res.group('xxx'))  # 10105199812067
print(res.group('ooo'))  # 023

 

五、正则实战案例

  在红牛官网上筛选出所有分公司的信息

import re

# 读取带匹配的数据
with open(r'a.txt', 'r', encoding='utf8') as f:
    data = f.read()
# 利用正则匹配数据
# 分公司名称
title_list = re.findall('<h2>(.*?)</h2>', data)
# print(title_list)
# 分公司地址
address_list = re.findall("<p class='mapIco'>(.*?)</p>", data)
# print(address_list)
# 分公司邮箱
email_list = re.findall("<p class='mailIco'>(.*?)</p>", data)
# print(email_list)
# 分公司电话
phone_list = re.findall("<p class='telIco'>(.*?)</p>", data)

res = zip(title_list, address_list, email_list, phone_list)
for data_tuple in res:
    print("""
    公司名称:%s
    公司地址:%s
    公司邮箱:%s
    公司电话:%s
    """ % (data_tuple[0], data_tuple[1], data_tuple[2], data_tuple[3]))

 

六、collections模块

  该模块内部提供了一些高阶的数据类型

  1. namedtuple(具名元组)

from collections import namedtuple

"""
namedtuple('名称',[名字1,名字2,...])
namedtuple('名称','名字1 名字2 ...')
"""
point = namedtuple('坐标', ['x', 'y'])
res = point(11, 22)
print(res)  # 坐标(x=11, y=22)
print(res.x)  # 11
print(res.y)  # 22
point = namedtuple('坐标', 'x y z')
res = point(11, 22, 33)
print(res)  # 坐标(x=11, y=22, z=33)
print(res.x)  # 11
print(res.y)  # 22
print(res.z)  # 33
card = namedtuple('扑克', '花色 点数')
card1 = card('', 'A')
card2 = card('', 'K')
print(card1)
print(card1.花色)
print(card1.点数)

  2. queue(队列)

import queue  # 内置队列模块:FIFO

# 初始化队列
q = queue.Queue()
# 往队列中添加元素
q.put('first')
q.put('second')
q.put('third')
# 从队列中获取元素
print(q.get())
print(q.get())
print(q.get())
print(q.get())  # 值去没了就会原地等待

  3. deque(双端队列)

from collections import deque

q = deque([11, 22, 33])
q.append(44)  # 从右边添加
q.appendleft(55)  # 从左边添加
print(q.pop())  # 从右边取值
print(q.popleft())  # 从左边取值

  4. 有序字典

normal_dict = dict([('name', 'jason'), ('pwd', 123), ('hobby', 'study')])
print(normal_dict)  # {'hobby': 'study', 'pwd': 123, 'name': 'jason'}
from collections import OrderedDict

order_dict = OrderedDict([('name', 'jason'), ('pwd', 123), ('hobby', 'study')])
print(order_dict)
OrderedDict([('name', 'jason'), ('pwd', 123), ('hobby', 'study')])
order_dict['xxx'] = 111
print(order_dict)
OrderedDict([('name', 'jason'), ('pwd', 123), ('hobby', 'study'), ('xxx', 111)])
normal_dict['yyy'] = 222
print(normal_dict)  # {'hobby': 'study', 'pwd': 123, 'yyy': 222, 'name': 'jason'}

  5. 默认值字典

from collections import defaultdict

values = [11, 22, 33, 44, 55, 66, 77, 88, 99, 90]
my_dict = defaultdict(list)
for value in values:
    if value > 60:
        my_dict['k1'].append(value)
    else:
        my_dict['k2'].append(value)
print(my_dict)

  6. 计数器

    1)传统方式

res = 'abcdeabcdabcaba'
# 统计字符串中每个元素出现的次数
new_dict = {}
for i in res:
    if i not in new_dict:
        new_dict[i] = 1
    else:
        new_dict[i] += 1
print(new_dict)

    2)使用计数器

from collections import Counter  # 计数器

res = 'abcdeabcdabcaba'
ret = Counter(res)
print(ret)

 

七、time模块

  时间三种表现形式:

    1)时间戳(秒数)

    2)结构化时间(一般是给机器看的)

    3)格式化时间(一般是给人看的)

    三种时间是可以相互转换的!!!

  1. time.sleep()  # 原地阻塞指定的秒数

  2. time.time()  # 获取时间戳时间

  3. 格式化时间

import time

print(time.strftime('%Y-%m-%d'))  # 2021-11-25
print(time.strftime('%Y-%m-%d %H:%M:%S'))  # 2021-11-25 11:48:34
print(time.strftime('%Y-%m-%d %X'))  # 2021-11-25 11:48:34
print(time.localtime())

  4.结构化时间和格式化时间转换

import time

print(time.time())
print(time.gmtime(1637840569))
print(time.localtime())

 

八、datetime模块

  1. date.today()和datetime.today()

    date年月日  datetime年月日时分秒  time时分秒(MySQL django后期可以)

import datetime

print(datetime.date.today())  # 2021-11-25
print(datetime.datetime.today())  # 2021-11-25 12:15:11.969769

  2. 获取年月日和星期

import datetime

res = datetime.datetime.today()
print(res.year)  # 2021
print(res.month)  # 11
print(res.day)  # 25
print(res.weekday())  # 获取星期(weekday星期是0-6) 0表示周一
print(res.isoweekday())  # 获取星期(weekday星期是1-7) 1表示周一

  3. timedelta(时间差)

    日期对象 = 日期对象 +/- timedelta对象

    timedelta对象 = 日期对象 +/- 日期对象

import datetime

ctime = datetime.datetime.today()
time_tel = datetime.timedelta(days=3)
print(ctime)  # 2021-11-25 12:20:48.570489
print(ctime - time_tel)  # 2021-11-22 12:21:06.712396
print(ctime + time_tel)  # 2021-11-28 12:21:06.712396
ret = ctime + time_tel
print(ret - ctime)  # 3 days, 0:00:00
print(ctime - ret)  # -3 days, 0:00:00

  4. 计算生日

import datetime

birthday = datetime.date(2022, 2, 3)
now_date = datetime.date.today()
days = birthday - now_date
print('距离生日还有{}天'.format(days))

  5. 时区

    UTC时间与我们的东八区时间差八个小时

import datetime

print(datetime.datetime.now())  # 2021-11-25 19:57:04.114215
print(datetime.datetime.utcnow())  # 2021-11-25 11:57:04.114215

posted @ 2021-11-25 20:00  尤露  阅读(284)  评论(0)    收藏  举报