标签:总结 10 logging res 30 re 模块 print md5
10月30总结
一、正则表达式
正则表达式是一些特殊的符号组合在一起产生一些特殊含义,它能帮助我们方便的检查一个字符串中符合条件的数据值。
正则表达式线上测试网址:http://tool.chinaz.com/regex/
二、正则表达式之字符组
字符组就是一组字符,在正则表达式中,列出用[]之间所有的字符。简单的字符组比如[0-9]、[a-z]、[A-Z]等。
1.[0-9] 列出字符组中0到9之间的任意数字:
字符组:"0123ab456cd789"
正则表达式:[0-9]
结果是:[0123456789]
2.[a-z] 列出字符组中a到z之间的任意字母
字符组:"abcd1ef2ghi98z"
正则表达式:[a-z]
结果是:[abcdefghiz]
3.[A-Z] 列出字符组中A到Z之间的任意字母:
字符组:"AB12CD3abEFZ"
正则表达式:[A-Z]
结果是:[ABCDEFZ]
ps:字符组在没有量词修饰的情况一次只会针对一个数据值。
三、正则表达式之特殊符
1 |
符号 |
含义 |
2 |
. |
匹配除换行符外的任意字符 |
3 |
\w |
匹配字母或数字或下划线 |
4 |
\W |
匹配非字母或数字或下划线 |
5 |
\d |
匹配数字 |
6 |
^ |
匹配字符串的开头 |
7 |
$ |
匹配字符串的结尾 |
8 |
| |
或;a|b:匹配a或b |
9 |
() |
给正则表达式分组,不影响正则表达式的匹配 |
10 |
[] |
匹配字符组中的字符 |
11 |
[^] |
匹配除了字符组中字符的所有字符 |
四、正则表达式之特殊符
编号 |
符号 |
量词 |
1 |
* |
重复零次或更多次(默认尽可能多) |
2 |
+ |
重复一次或更多次(默认尽可能多) |
3 |
? |
重复零次或一次(默认一次) |
4 |
{n} |
重复n次 |
5 |
{n,} |
重复n次或更多次 |
6 |
{n,m} |
重复n到m次 |
五.贪婪匹配与非贪婪匹配
1.贪婪匹配
默认都是贪婪匹配
2.非贪婪模式
只需要在量词后面加上"?"就可以让贪婪匹配变成非贪婪匹配
ps:以后我们在使用贪婪匹配或者非贪婪匹配的时候一般都是用“.*”或“.*?”,并且结束的标志有上述符号左右两边添加的表达式绝对。
六、转义符
1.使用场景
当要匹配没有没有换行含义的"\n"时需要取消它自带的换行含义
2.使用方式
在正则表达式中取消转义使用 "\" (每个"\"只能取消一个字符的转义)
#斜杠与字母的组合有时候有特殊含义
\n 匹配的是换行符
\\n 匹配的是文本\n
\\\\n 匹配的是文本\\n
ps:如果是在python中使用 还可以在字符串前面加r取消转义
七、re模块
在python中想要使用正则表达式 re模块是其中选择之一。
re模块的常用方法:
序号 |
方法 |
用法 |
1 |
findall |
列出字符串中模式的所有匹配项 |
2 |
finditer |
将所有匹配到的项生成一个迭代器 |
3 |
search |
在字符串中查找 。第一个匹配到的对象或者None(返回一个match对象) |
4 |
match |
在字符串的开始处匹配模式。 字符串开始没有则 None(返回一个match对象) |
5 |
compile |
提前设置好正则表达式后面可以直接调用 |
6 |
match.group(index) |
将match对象拆分成字符串。不写index默认是0 |
7 |
match.groups() |
将match对象转换成元组 |
import re # 别忘了导包
res = re.findall('a','aa and bb and abc')
print(res)
# ['a', 'a', 'a', 'a', 'a']
res = re.finditer('a','aa and bb and abc')
print(res) # <callable_iterator object at 0x7f9c1aba5f70> 迭代器
res = re.search('a','aa and bb and abc')
print(res) # <re.Match object; span=(0, 1), match='a'>
print(res.group()) # a
res = re.match('a','aa and bb and abc')
print(res) # None
obj = re.compile('a')
print(re.findall(obj,'asdccecaawsa')) # ['a', 'a', 'a', 'a']
print(re.findall(obj,'dsfsaaecacek')) # ['a', 'a', 'a']
八、re模块之()用法
1.分组优先
import re
res = re.findall('and','aandbandcandabc')
print(res) # ['and', 'and', 'and']
res = re.findall('a(n)d','aandbandcandabc')
print(res) # ['n', 'n', 'n']
'''
findall针对分组的正则表达式匹配到的结果优先显示
可以用 (?:)取消优先显示'''
res = re.findall('a(?:n)d','aandbandcandabc')
print(res) # ['and', 'and', 'and']
2.取别名
import res
res = re.search('a(?P<id>b)(?P<name>c)','abcabcabcabc')
print(res.group()) # abc
print(res.group(1)) # b
print(res.group('id')) # b
print(res.group('name')) # c
九、第三方模块简介
1.第三方模块的用处
python之所以在这么多的编程语言中脱颖而出的优点是有众多的第三方库函数,可以更高效率的实现开发
2.第三方模块的使用
1.第三方模块必须下载才能使用
格式:pip install 模块名 -i 源地址
清华大学 :https://pypi.tuna.tsinghua.edu.cn/simple/
阿里云:http://mirrors.aliyun.com/pypi/simple/
中国科学技术大学 :http://pypi.mirrors.ustc.edu.cn/simple/
华中科技大学:http://pypi.hustunique.com/
豆瓣源:http://pypi.douban.com/simple/
腾讯源:http://mirrors.cloud.tencent.com/pypi/simple
华为镜像源:https://repo.huaweicloud.com/repository/pypi/simple/
2.可在终端借助pip工具下载
格式:
下载第三方模块的句式:pip install 模块名
下载第三方模块临时切换仓库的句式:pip install 模块名 -i 仓库地址
下载第三方模块指定版本(不指定默认是最新版):pip install 模块名 == 版本号 -i 仓库地址
注:在下载解释器pip解释器工具的时候,电脑上有多个版本的解释器时一定要注意到底用的是哪一个,在使用或者添加的时候一定要看清楚对应的版本号
3.在pycharm中也可以直接下载
![图片名称](/i/l/?n=22&i=blog/2781968/202210/2781968-20221026185438283-765188898.jpg)
3.下载第三方模块的注意点
1.pip版本过低并有警告信息
# WARNING: You are using pip version 20.3.1;
原因是pip版本过低,只需要输入命令行更新模块就好了
python -m pip install --upgrade pip
2.报错含有Timeout关键字
说明当前计算机的网络不稳定,只需要换网或者程序执行几次即可
3.报错没有关键字
将关键字复制到百度进行搜索,然后进行解决
4.下载速度很慢
pip默认下载的仓库地址是国外的 python.org
我们可以切换下载的地址
pip install 模块名 -i 仓库地址
pip的仓库地址有很多 百度查询即可
十、网络爬虫基础实战
import requests
import re
headers = {
'user-agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.0.0 Safari/537.36'
}
res = requests.get('http://www.redbull.com.cn/about/branch', headers=headers)
data = res.text
res.encoding = 'utf-8' # 可以直接用utf-8对数据进行转码
with open(r'hn.html', 'wb') as f:
f.write(res.content)
# 1.获取所有的分公司名称
company_name_list = re.findall('<h2>(.*?)</h2>', data)
# 2.获取所有的分公司地址
company_addr_list = re.findall("<p class='mapIco'>(.*?)</p>", data)
# 3.获取所有的分公司邮箱
company_email_list = re.findall("<p class='mailIco'>(.*?)</p>", data)
# 4.获取所有的分公司电话
company_phone_list = re.findall("<p class='telIco'>(.*?)</p>", data)
# 5.将上述四个列表中的数据按照位置整合
res = zip(company_name_list, company_addr_list, company_email_list, company_phone_list)
# 6.处理数据(展示 保存 excel)
for i in res:
print("""
----------------------------公司名称:%s----------------------------
公司地址:%s
公司邮箱:%s
公司电话:%s
-----------------------------------------------------------------------------
""" % i)
![图片名称](/i/l/?n=22&i=blog/2781968/202210/2781968-20221026185518859-862919216.png)
十一、openpyxl模块
1.openpyxl模块的作用
主要用于操作excel表格,实现自动化办公
2.Excel文件的后缀名的问题
03版本之前 ---->>> .xls
03版本之后 ---->>> .xlsx
3.操作excel表格的第三方模块
xlwt往表格写入数据、wlrd从表格读取数据
兼容性强
openpyxl最近几年比较火热的操作excel表格的模块
03版本之前的兼容性较差
实战:
from openpyxl import Workbook
user_excel = Workbook() # 创建excel
grades = user_excel.create_sheet('成绩表') #成绩表
physique = user_excel.create_sheet('体质表') #体质表
name = user_excel.create_sheet('姓名表',0) #姓名表
physique.title = '体能表'
name.sheet_properties.tabColor = '8B0000' #修改姓名表的颜色
# 第一种写入方式
name['A1'] = '小明同学'
name['B1'] = '男'
# 第二种写入方式
name.cell(row=1, column=3, value='28')
name.cell(row=1, column=4, value='小菜鸡')
# 第三种写入方式(批量写入)
name.append(['小红同学', '女', '18', '貌美如花'])
name.append(['小天同学','男', '20', '一顿能吃'])
name.append(['小维同学', '男', 18, '多看书'])
user_excel.save(r'user_excel.xlsx') # 保存文件
十二、hashlib加密模块
1.加密模块简介
1.加密模块简介
将明文数据进行加密处理,转变为密文数据再存储或者传输,这样的安全机制可以让用户的数据不容易泄露,一般情况下一串没有规则的数字字母组合一般都是加密之后的结果,密文越长表示使用的加密算法(数据的处理过程)越复杂
2.常见的加密算法
md5,base64,hmac,sha系列(sha1,sha2,sha3)
2.加密模块的md5加密
import hashlib
md5 = hashlib.md5() #md5加密
md5.update(b'useranme') #数据类型必须是bytes
res = md5.hexdigest() #获取加密后的结果
print(res) # 78d8856b5c6cab3ffe28552bcbdf15e8
3.额外的知识点
import hashlib
md5 = hashlib.md5() #md5加密
md5.update(b'useranme~pwd') #数据类型必须是bytes
# md5.update(b'useranme~') #数据类型必须是bytes
# md5.update(b'pwd') #数据类型必须是bytes
res = md5.hexdigest() #获取加密后的结果
print(res) # 结果都是19627664f7c9922385641fba9e511cfd
# 加密算法不变,内容如果相同,那么结果一定相同
# 加密之后的结果是无法反向解密的,只能从明文到密文推导,不能密文到明文推导
4.加盐处理
import hashlib
md5 = hashlib.md5() #md5加密
md5.update('设置的干扰项目'.encode('utf8'))
md5.update(b'useranme~pwd') #数据类型必须是bytes
res = md5.hexdigest() #获取加密后的结果
print(res)
1.因为加盐处理也是人为设定的一个值,所以也不太安全,所以我们选择动态加盐
2.加密之后的结果一般不能反解码
3.当加密大文件时,如果将全部加密的话那样太慢了,所以要操作进行优化截取一部分的内容进行分段加密
十三、subprocess远程命令模块
subprocess的作用:
模拟操作系统终端,执行命令并获取结果
import subprocess
cmd = input('请输入您的指令>>>').strip()
res = subprocess.Popen(
cmd, #操作系统要执行的命令
shell=True, #固定配置
stdin=subprocess.PIPE, #输入命令
stdout=subprocess.PIPE, #输出命令
)
print(res.stdout.read().decode('gbk'))
print(res.stderr.read().decode('gbk'))
十四、logging日志模块
1.日志的作用
日志的作用就是记录程序在运行过程中发生的记录,日志文件数据写完后基本不会去改动,需要放到配置文件中
2.日志的等级
logging.debug('debug等级') # 10
logging.info('info等级') # 20
logging.warning('warning等级') # 默认从warning级别开始记录日志 30
logging.error('error等级') # 40
logging.critical('critical等级') # 50
日志级别等级CRITICAL > ERROR > WARNING > INFO > DEBUG)
3.日志的应用
import logging
# logging.debug('debug message')
# logging.info('info message')
# logging.warning('warning message')
# logging.error('error message')
# logging.critical('critical message')
file_handler = logging.FileHandler(filename='x11.log', mode='a', encoding='utf-8', )
logging.basicConfig(
format='%(asctime)s - %(name)s - %(levelname)s -%(module)s: %(message)s',
datefmt='%Y-%m-%d %H:%M:%S %p',
handlers=[file_handler, ],
level=logging.ERROR
)
logging.error('我就是我,不一样的烟火')
![图片名称](/i/l/?n=22&i=blog/2781968/202210/2781968-20221027183704438-1737037917.png)
4.固定的配置字典
import logging
import logging.config
# 定义日志输出格式 开始
standard_format = '[%(asctime)s][%(threadName)s:%(thread)d][task_id:%(name)s][%(filename)s:%(lineno)d]' \
'[%(levelname)s][%(message)s]' # 其中name为getlogger指定的名字
simple_format = '[%(levelname)s][%(asctime)s][%(filename)s:%(lineno)d]%(message)s'
# 自定义文件路径
logfile_path = 'a3.log'
# log配置字典
LOGGING_DIC = {
'version': 1,
'disable_existing_loggers': False,
'formatters': {
'standard': {
'format': standard_format
},
'simple': {
'format': simple_format
},
},
'filters': {}, # 过滤日志
'handlers': {
# 打印到终端的日志
'console': {
'level': 'DEBUG',
'class': 'logging.StreamHandler', # 打印到屏幕
'formatter': 'simple'
},
# 打印到文件的日志,收集info及以上的日志
'default': {
'level': 'DEBUG',
'class': 'logging.handlers.RotatingFileHandler', # 保存到文件
'formatter': 'standard',
'filename': logfile_path, # 日志文件
'maxBytes': 1024 * 1024 * 5, # 日志大小 5M
'backupCount': 5,
'encoding': 'utf-8', # 日志文件的编码,再也不用担心中文log乱码了
},
},
'loggers': {
# logging.getLogger(__name__)拿到的logger配置
'': {
'handlers': ['default', 'console'], # 这里把上面定义的两个handler都加上,即log数据既写入文件又打印到屏幕
'level': 'DEBUG',
'propagate': True, # 向上(更高level的logger)传递
}, # 当键不存在的情况下 (key设为空字符串)默认都会使用该k:v配置
# '购物车记录': {
# 'handlers': ['default','console'], # 这里把上面定义的两个handler都加上,即log数据既写入文件又打印到屏幕
# 'level': 'WARNING',
# 'propagate': True, # 向上(更高level的logger)传递
# }, # 当键不存在的情况下 (key设为空字符串)默认都会使用该k:v配置
},
}
logging.config.dictConfig(LOGGING_DIC) # 自动加载字典中的配置
# logger1 = logging.getLogger('购物车记录')
# logger1.warning('尊敬的VIP客户 晚上好 您又来啦')
# logger1 = logging.getLogger('注册记录')
# logger1.debug('jason注册成功')
logger1 = logging.getLogger('体测登记表')
logger1.debug('小帅哥')
![图片名称](/i/l/?n=22&i=blog/2781968/202210/2781968-20221027183923125-1377205598.png)
5.日志的组成
(1).产生日志 (logger)
(2).过滤日志 (filter)
(3).输出日志 (handler)
(4).日志格式 (format)
标签:总结,
10,
logging,
res,
30,
re,
模块,
print,
md5
From: https://www.cnblogs.com/zx0524/p/16842224.html