01 今日内容大纲
-
自定义模块
-
模块是什么?
-
为什么要有模块?
- 什么是脚本?
-
模块的分类
-
import 的使用
- 第一次导入模块执行三件事
- 被导入模块有独立的名称空间
- 为模块起别名
- 导入多个模块
-
from xxx import xxx
- from xxx import xxx 的使用
- from xxx import xxx 与 import 对比
- 一行导入多个
- from xxx import xxx 星
- 模块循环导入的问题
- py文件的两种功能
- 模块的搜索路径
-
json pickle 模块
-
hashlib 模块
02 昨日内容回顾
03 今日内容
-
自定义模块
-
模块是什么?
-
模块就是一个py文件常用的相似的功能集合.
-
抖音: 20万行代码全部放在一个py文件中?
-
为什么不行?
#1.代码太多,读取代码耗时太长 #2.代码不容易维护
-
所以我们怎么样:
#一个py文件拆分100文件,100个py文件又有相似相同的功能.冗余. 此时你要将100个py文件中相似相同的函数提取出来, input 功能,print()功能, time.time() os.path.....放在一个文件,当你想用这个功能拿来即用.类似于这个py文件: 常用的相似的功能集合.模块.
-
-
为什么要有模块?
#1.拿来主义,提高开发效率 #2.便于管理维护
-
什么是脚本?
#脚本就是py文件.长期保存代码的文件
-
-
模块的分类
-
内置模块200种左右.Python解释器自带的模块,time os sys hashlib等等
-
第三方模块6000种.一些大牛大神写的,非常好用的
- pip install 需要这个指令安装的模块,Beautiful_soup,request,Django,flask 等等
-
自定义模块,自己写的一个py文件.
-
-
import 的使用
-
第一次导入模块执行三件事 (重要!!!!!!!!)
#1.在内存中创建一个以tbjx命名的名称空间. #2.执行此名称空间所有的可执行代码(将tbjx.py文件中所有的变量与值的对应关系加载到这个名称空间). #3.通过tbjx. 的方式引用模块里面的代码
-
被导入模块有独立的名称空间
import tbjx name = 'alex' print(name) print(tbjx.name) def read1(): print(666) tbjx.read1() name = '日天' tbjx.change() print(name) # 日天 print(tbjx.name) # barry
-
为模块起别名
-
简单方便
import tbjx as sm print(sm.name)
-
利于代码的简化
#原始写法 result = input('请输入') if result == 'mysql': import mysql1 mysql1.mysql() elif result == 'oracle': import oracle1 oracle1.oracle() list.index() str.index() tuple.index() #起别名 result = input('请输入') if result == 'mysql': import mysql1 as sm elif result == 'oracle': import oracle1 as sm # ...... sm.db() # 统一接口,归一化思想
-
-
导入多个模块
import time, os, sys # 这样写不好 import time import os import sys
-
-
from xxx import xxx
-
from xxx import xxx 的使用
from tbjx import name from tbjx import read1 from tbjx import read2 print(name) print(globals()) read1()
-
from xxx import xxx 与 import 对比
-
前者更方便
from tbjx import name print(name)
-
前者容易产生冲突,产生覆盖(就近原则)
name = 'alex' from tbjx import name print(name)
-
-
当前位置直接使用read1和read2,执行时,仍然以tbjx.py文件全局名称空间 (重要!!!!!!!!!!)
from tbjx import read1 def read1(): print(666) name = '大壮' read1() print(globals()) from tbjx import change name = 'Alex' print(name) # 'Alex' change() # 'barry' from tbjx import name print(name)
-
一行导入多个
from tbjx import name,read1,read2 # 这样不好 from tbjx import name from tbjx import read1
-
from xxx import xxx 星
#一般千万别么这写,必须要将这个模块中的所有名字全部记住 #但是可以配合一个变量使用 __all__ = ['name', 'read1'] # 配合*使用
-
模块循环导入的问题
-
py文件的两种功能
- 自己使用 脚本
- 被他人使用 模块
name = '太白金星' def read1(): print('tbjx模块:', name) def read2(): print('tbjx模块') read1() def change(): global name name = 'barry' print(name) # print(__name__) # 当tbjx.py做脚本: __name__ == __main__ 返回True # 当tbjx.py做模块被别人引用时: __name__ == tbjx # __name__ 根据文件的扮演的角色(脚本,模块)不同而得到不同的结果 #1, 模块需要调试时,加上 if __name__ == '__main__': # import time # change() # 测试代码 # if __name__ == '__main__': # change()
-
模块的搜索路径
# 搜索的路径: import sm import abc # python 解释器会自动将一些内置内容(内置函数,内置模块等等)加载到内存中 import sys # print(sys.modules) # 内置内容(内置函数,内置模块等等) import time print(sys.path) ['D:\python_22\day17', 'C:\Python\Python36\python36.zip', 'C:\Python\Python36\DLLs', 'C:\Python\Python36\lib', 'C:\Python\Python36', 'C:\Python\Python36\lib\site-packages'] 'D:\python_22\day17' 路径是当前执行文件的相对路径 import tbjx # 我就想找到dz 内存没有,内置中,这两个你左右不了,sys.path你可以操作. import sys sys.path.append(r'D:python_22day16') # sys.path 会自动将你的 当前目录的路径加载到列表中. import dz # 如果你想要引用你自定义的模块: # 要不你就将这个模块放到当前目录下面,要不你就手动添加到sys.path
-
-
json pickle 模块
-
序列化模块:将一种数据结构(list,tuple,dict ....)转化成特殊的序列
-
为什么存在序列化?
#数据 ----> bytes #只有字符串类型和bytes可以互换 #dict,list..... -------> str <--------> bytes #数据存储在文件中,str(bytes类型)形式存储,比如字典 #数据通过网络传输(bytes类型),str 不能还原回去 #特殊的字符串:序列化
-
json模块(重点!!!!!!!!!!!!!!!!!!!!!!!!!!!)
-
不同语言都遵循的一种数据转化格式,即不同语言都使用的特殊字符串。(比如Python的一个列表[1, 2, 3],利用json转化成特殊的字符串,然后在编码成bytes发送给php的开发者,php的开发者就可以解码成特殊的字符串,然后在反解成原数组(列表): [1, 2, 3])
-
json序列化只支持部分Python数据结构:dict,list, tuple,str,int, float,True,False,None(元组转化成列表,转回时不可转回元组,只能转成列表)
l1 = [i for i in range(10)] # print(l1) # l1---->bytes s1 = str(l1) b1 = s1.encode('utf-8') print(b1) # 岑哥接收到了b1 s2 = b1.decode('utf-8') print(s2,type(s2)) dic = {'username':'太白','age':18} import json # dumps loads 主要用于网络传输,也可以读写文件 # 特殊的字符串 st = json.dumps(dic,ensure_ascii=False) print(st,type(st)) # 翻转回去 st = json.loads(st) print(st,type(st)) # 写入文件 import json l1 = [1,2,3,{'name':'json'}] # 转化成特殊的字符串写入文件当中 st = json.dumps(l1) with open('json文件1.txt',encoding='utf-8',mode='w') as f1: f1 = f1.write(st) print(type(st)) # 读取数据 with open('json文件1.txt',encoding='utf-8',mode='r') as f1: s = f1.read() print(s,type(s)) # 一次性写入多个文件如何操作? import json dic1 = {'username': 'alex'} dic2 = {'username': '太白'} dic3 = {'username': '大壮'} # 写入 with open('json文件1.txt',encoding='utf-8',mode='w') as f1: f1.write(json.dumps(dic1)+' ') f1.write(json.dumps(dic2)+' ') f1.write(json.dumps(dic3)+' ') # 读取 with open('json文件1.txt',encoding='utf-8',mode='r')as f2: for i in f2: print(json.loads(i))
-
-
pickle 模块
-
只能是Python语言遵循的一种数据转化格式,只能在python语言中使用
-
支持Python所有的数据类型包括实例化对象
l1 = [1, 2, 3, {'name': 'alex'}] # dumps loads只能用于网络传输 import pickle bt = pickle.dumps(l1) print(bt,type(bt)) #<class 'bytes'> l2 = pickle.loads(bt) print(l2,type(l2)) # <class 'list'> # dump load 直接写入文件 import pickle dic1 = {'name':'oldboy1'} dic2 = {'name':'oldboy2'} dic3 = {'name':'oldboy3'} f = open('pickle数据.txt',mode='wb') #不用utf-8 pickle.dump(dic1,f) pickle.dump(dic2,f) pickle.dump(dic3,f) f.close() import pickle with open('pickle数据.txt',mode='rb')as f: print(pickle.load(f)) print(pickle.load(f)) print(pickle.load(f)) import pickle def func(): print('in func') f = open('pick对象',mode='wb') pickle.dump(func,f) f.close() f = open('pick对象',mode='rb') ret = pickle.load(f) print(ret,type(ret))
-
-
-
hashlib 模块
-
包含很多加密算法:MD5, sha1 sha256 sha512等等
-
hashlib 用途:
- 密码加密,不能以明文的形式存储密码,以密文的形式
- 文件的校验
-
hashlib 用法:
- 将bytes类型字节 转化成 固定长度的16进制数字组成的字符串
- 不同的bytes利用相同的算法(MD5)转化成的结果一定不同
- 相同的bytes利用相同的算法(MD5)转化成的结果一定相同
- hashlib算法不可逆(MD5中国王晓云破解了)
# import hashlib # hashlib.md5() # md5 s1 = 'asjdhkjhfdsjhsdjfhsdhfhoiweuriweur' import hashlib obj = hashlib.md5() obj.update(s1.encode('utf-8')) #Unicode-objects must be encoded before hashing print(obj.hexdigest()) # 相关练习 登录加密模块 import hashlib def MD5(password): ret = hashlib.md5() ret.update(password.encode('utf-8')) return ret.hexdigest() def register(): while 1: username = input('请输入用户名').strip() if username.upper() == 'Q': print('您已退出') break else: password = input('请输入密码').strip() password_md5 = MD5(password) with open('register.txt',encoding='utf-8',mode='a')as f1: f1 = f1.write(f'{username}丨{password_md5}'+' ') register() # def login(): # username = input('请输入用户名').strip() # password = input('请输入密码').strip() # password_md5 = MD5(password) # 普通加密 import hashlib s1 = 'lksjgkdfjhdjfhgdhfkjdfhgkjdfg' s2 = 'jakhdqwtyeiqwuyeqyiuqwye' ret = hashlib.md5() ret.update(s2.encode('utf-8')) print(ret.hexdigest()) #de232ee267bb2577552144094045470d # 加盐 import hashlib s2 = 'jakhdqwtyeiqwuyeqyiuqwye' ret = hashlib.md5('理由一赔'.encode('utf-8')) ret.update(s2.encode('utf-8')) print(ret.hexdigest()) #9ad9aea3fa7bc41dbe6280194f5e4e91 # 动态的盐 import hashlib s2 = 'jakhdqwtyeiqwuyeqyiuqwye' ret = hashlib.md5('理由一赔'[::2].encode('utf-8')) ret.update(s2.encode('utf-8')) print(ret.hexdigest()) #963d8512b005ff6291cb89c3080f6fd0 # sha系列:金融类,安全类 # 随着sha系列数字越高,加密越复杂,越不易破解,但是耗时越长 import hashlib s2 = 'jakhdqwtyeiqwuyeqyiuqwye' ret = hashlib.sha3_384() ret.update(s2.encode('utf-8')) print(ret.hexdigest()) #5f7e9ddf96f13795df0012e8b937e0e54c013654045eace8402dc68b997330e6bdcd8a17735e4b0c0e43a7fd29c647c0 # 文件的校验 # linux中一切皆文件:文本文件,非文本文件:音频 视频 图片 # 无论你下载的视频还是文件,还是软件(国外的软件),往往都会有一个md5值 # 低端版校验: import hashlib def file_md5(path): ret = hashlib.md5() with open(path,mode='rb')as f: f = f.read() ret.update(f) return ret.hexdigest() result = file_md5(r'C:UsersPengDownloadspython-3.8.5-amd64.exe') print(result) #0ba2e9ca29b719da6e0b81f7f33f08f6 # 高级版校验(大文件拆分,每次读取16个字节): # python 3.8.5 0ba2e9ca29b719da6e0b81f7f33f08f6` def hash(path): import hashlib with open(path,mode='rb') as f1: obj = hashlib.md5() while 1: segbytes = f1.read(16) if segbytes: obj.update(segbytes) else: break print(obj.hexdigest()) hash(r'C:UsersPengDownloadspython-3.8.5-amd64.exe')
-
04 今日总结
-
import 三件事
- 创建一个以模块名命名的名称空间
- 模块内的可执行代码全部执行一次(将文件中所有的变量与值的对应关系加载到这个名称空间)
- 以模块名.的方式调用模块中的函数及变量
-
from xxx import xxx
- 容易产生冲突
- 引用的函数及变量依然在独立的空间
-
__name__
的问题 -
模块的搜索路径
#内存--->内置--->sys.path
-
序列化模块:
- json最最常用(两对四个方法就行) 一定要掌握
- pickle(两对四个方法就行) 尽量掌握
-
hashlib
- 密码的加密
- 文件的校验
05 明日复习
规范化目录结构