一、模块(module)
为了方便维护代码,可以将不同功能的代码分组,保存在不同的文件里。这样,每个文件包含的代码量就会比较少,更方便维护。
在Python中,一个.py文件就可以称之为一个模块。
即:
- 包含相应功能的函数以及变量,Python则以".py" 为后缀名
- 模块可以为其他的程序引用,以使用该模块所对应的函数或者变量
1.1 优点
- 提高代码的可维护性
- 提高代码的复用性
- 可以导入很多功能的模块(标准库模块、第三方模块、自定义模块)
- 避免变量名重复(作用域)
1.2 Python中导入模块的常用方式
import 模块名称
import 模块名称 as 新名称
from 模块名称 import 函数名
区别:
import 模块名称
和import 模块名称 as 新名称
- 会导入整个模块
- 如果我们需要使用某个函数,必须以"模块名称. 函数名()"的形式来调用相应的函数(这种方法可以更有利于代码的可读性)
import 模块名称 as 新名称
重新命名导入的模块,通常使模块名称简洁,方便使用
from 模块名称 import 函数名
- 只导入了某一函数,而不是一整个模块
- 可以直接函数名称取调用函数,无需在函数名称前面加模块名称
- 如果我们的程序语句很多,不建议采用此种方法(原因:调用很多模块后,可能会造成函数名称重复,引发错误)
注意
import 语句的对应模块顺序(PEP)
- Python标准模块
- 第三方
- 自定义模块
1.3 自定义模块
#module_test.py
a = 14
import module_test
print(module_test.a) #14
二、OS 模块
OS模块是Python标准库中用于访问操作系统功能的模块
使用OS模块提供的接口,能够实现跨平台访问
最常见的操作:
- 目录的操作
- 判断
2.1 系统操作
- os.sep:用于查看系统路径的分隔符
- Windows:"\\"
- Linux/Unix:"/"
- os.name:显示我们正在使用的平台
- Windows:“nt”
- Linux/Unix:“posix”
- os.getenv( ):读取环境变量
- os.getcwd( ):返回当前工作目录
2.2 目录操作
查
- os.listdir(path):返回指定目录下的所有文件和目录名
>>> import os
>>> os.listdir()
['.idea', 'file', 'module_test.py', 'test190716-17.py', 'test190718.py', 'test190719.py', 'test190722.py', '__pycache__']
增
- os.mkdir(path):只能创建一级
- os.makedirs(path):可以创建多级
>>> import os
>>> os.mkdir('111')
>>> os.listdir()
['.idea', '111', 'file', 'module_test.py', 'test190716-17.py', 'test190718.py', 'test190719.py', 'test190722.py', '__pycache__']
>>> os.chdir('file')
>>> os.makedirs('test\\test1')
>>> os.listdir()
['GreenFlowerPorcelain.txt', 'random_100.txt', 'test', 'zht.txt', '啦啦啦.txt', '青花瓷.txt']
删
- os.rmdir(path):删除空目录(只能删一级)
- os.removerdirs(path):删除空目录(递归删除目录)
- os.remove(path):删除文件
>>> import os
>>> os.rmdir('111')
>>> os.listdir()
['.idea', 'file', 'module_test.py', 'test190716-17.py', 'test190718.py', 'test190719.py', 'test190722.py', '__pycache__']
>>> os.removedirs('test\\test1')
>>> os.listdir()
['GreenFlowerPorcelain.txt', 'random_100.txt', 'zht.txt', '啦啦啦.txt', '青花瓷.txt']
改
- os.chdir(path):更改到指定的目录
>>> import os
>>> os.getcwd()
'D:\\PycharmProjects\\untitled1'
>>> os.chdir('..')
>>> os.getcwd()
'D:\\PycharmProjects'
- os.rename(old,new):重命名文件或目录
>>> import os
>>> os.listdir()
['GreenFlowerPorcelain.txt', 'random_100.txt', '啦啦啦.txt', '张杭天.txt', '青花瓷.txt']
>>> os.rename( '张杭天.txt','zht.txt')
>>> os.listdir()
['GreenFlowerPorcelain.txt', 'random_100.txt', 'zht.txt', '啦啦啦.txt', '青花瓷.txt']
判断文件
- os.path.exists(path):判断文件或者目录是否存在,存在,True;否则,False
- os.path.isfile(path):判断是否为文件
- os.path.isdir(path):判断是否为目录
>>> import os
>>> os.listdir()
['GreenFlowerPorcelain.txt', 'random_100.txt', 'zht.txt', '啦啦啦.txt', '青花瓷.txt']
>>> os.path.exists('zht.txt')
True
>>> os.path.exists('zht')
False
>>> os.listdir()
['.idea', 'file', 'module_test.py', 'test190716-17.py', 'test190718.py', 'test190719.py', 'test190722.py', '__pycache__']
>>> os.path.isdir('file')
True
>>> os.path.isfile('test190719.py')
True
- os.path.dirname(path):返回文件路径
- os.path.basename(path):返回文件名
- os.path.abspath(path):返回绝对路径
- os.path.getsize(path):返回文件大小,如果文件不存在就返回错误
- os.path.join(path1[, path2[, …]]):把目录和文件名合成一个路径
- os.path.split(path):把路径分割成 dirname 和 basename,返回一个元组
>>> import os
>>> os.listdir()
['GreenFlowerPorcelain.txt', 'random_100.txt', 'zht.txt', '啦啦啦.txt', '青花瓷.txt']
>>> os.path.dirname('zht.txt')
''
>>> os.path.basename('zht.txt')
'zht.txt'
>>> os.path.abspath('zht.txt')
'D:\\PycharmProjects\\untitled1\\file\\zht.txt'
>>> os.path.getsize('zht.txt')
12
>>> os.path.join('../file','zht.txt')
'../file\\zht.txt'
>>> os.path.split('D:\\PycharmProjects\\untitled1\\file\\zht.txt')
('D:\\PycharmProjects\\untitled1\\file', 'zht.txt')
查看文件的时间
- os.path.getmtime(path):返回文件或目录的最后修改时间,结果为秒数
- os.path.getatime(path):返回文件或目录的最后访问时间,结果为秒数
- os.path.getctime(path):返回文件或目录的创建时间,结果为秒数
>>> import os
>>> time.strftime('%Y-%m-%d %H:%M:%S',time.localtime(os.path.getctime('zht.txt')))
'2019-07-22 10:08:28'
>>> time.strftime('%Y-%m-%d %H:%M:%S',time.localtime(os.path.getatime('zht.txt')))
'2019-07-22 17:22:16'
>>> time.strftime('%Y-%m-%d %H:%M:%S',time.localtime(os.path.getmtime('zht.txt')))
'2019-07-22 17:19:48'
>>>
获取文件和目录
- os.walk(path)
>>> import os
>>> paths = os.walk('..')
>>> for i in paths:
... print(i)
...
('..', ['.idea', 'file', '__pycache__'], ['module_test.py', 'test190716-17.py', 'test190718.py', 'test190719.py', 'test190722.py'])
('..\\.idea', ['inspectionProfiles'], ['misc.xml', 'modules.xml', 'untitled1.iml', 'workspace.xml'])
('..\\.idea\\inspectionProfiles', [], [])
('..\\file', [], ['GreenFlowerPorcelain.txt', 'random_100.txt', 'zht.txt', '啦啦啦.txt', '青花瓷.txt'])
('..\\__pycache__', [], ['module_test.cpython-36.pyc'])
>>>
三、time模块
3.1 休眠函数
import time
time.sleep([n])
3.2 在Python中,表示时间通常有3中方式
- 时间戳(timetamp):表示从1970-01-01 00:00:00 开始按秒进行的偏移量
- 格式化的时间字符串(format string)
- 结构化的时间(struct_time):元组,9个元素(年月日时分秒,一年的第几周、第几天,夏令时)
获取当前时间戳
import time
time.time()
格式化的时间字符串
>>> import time
>>> time.strftime("%Y-%m-%d %H:%M:%S")
'2019-07-26 08:58:45'
>>>
python中时间日期格式化符号:
%y 两位数的年份表示(00-99)
%Y 四位数的年份表示(000-9999)
%m 月份(01-12)
%d 月内中的一天(0-31)
%H 24小时制小时数(0-23)
%I 12小时制小时数(01-12)
%M 分钟数(00=59)
%S 秒(00-59)
%a 本地简化星期名称
%A 本地完整星期名称
%b 本地简化的月份名称
%B 本地完整的月份名称
%c 本地相应的日期表示和时间表示
%j 年内的一天(001-366)
%p 本地A.M.或P.M.的等价符
%U 一年中的星期数(00-53)星期天为星期的开始
%w 星期(0-6),星期天为星期的开始
%W 一年中的星期数(00-53)星期一为星期的开始
%x 本地相应的日期表示
%X 本地相应的时间表示
%Z 当前时区的名称
%% %号本身
结构化的时间
>>> import time
>>> time.localtime()[0]
2019
序号 | 字段 | 属性 | 值 |
---|---|---|---|
0 | 4位数年 | tm_year | 2008 |
1 | 月 | tm_mon | 1 到 12 |
2 | 日 | tm_mday | 1 到 31 |
3 | 小时 | tm_hour | 0 到 23 |
4 | 分钟 | tm_min | 0 到 59 |
5 | 秒 | tm_sec | 0 到 61 (60或61 是闰秒) |
6 | 一周的第几日 | tm_wday | 0到6 (0是周一) |
7 | 一年的第几日 | tm_yday | 一年中的第几天,1 到 366 |
8 | 夏令时 | tm_isdst | 是否为夏令时,值有:1(夏令时)、0(不是夏令时)、-1(未知),默认 -1 |
3.3 time模块的常用方法
方法 | 描述 |
---|---|
time.localtime([sec]) | 将一个时间戳转化为一个当前时区的struct_time(默认为当前时间) |
time.gmtime([sec]) | 和localtime()类似,不同的是,它将一个时间戳转化为UTC时区(0时区)的struct_time |
time.time() | 返回当前时间戳 |
time.mktime(t) | 将time.struct_time转化为时间戳 |
time.sleep(sec) | 线程推迟指定的时间运行,单位(s) |
time.asctime([t]) | 把表时间的元组或 struct_time表示为:“Sun July 26 09:06:40 2019”(默认为time.localtime()) |
time.ctime([t]) | 把一个时间戳转换为time.asctime()的形式(默认time.time()) |
time.strftime(format,[t]) | 把一个代表时间的元组/struct_time(localtime()和gmtime())转化为格式化的字符串(默认为time.localtime()) |
time.strptime() | 将结构化字符串转换为 struct_time形式 |
- 时间戳,计算机识别
- 字符串时间,人类看的
- 结构化时间,对时间操作
3.4 时间转化
时间戳到结构化时间的转化
- time.gmtime(now)
- time.localtime(now)
>>> import time
>>> now = time.time()
>>> time.gmtime(now) #UTC时间
time.struct_time(tm_year=2019, tm_mon=7, tm_mday=26, tm_hour=1, tm_min=17, tm_sec=34, tm_wday=4, tm_yday=207, tm_isdst=0)
>>> time.localtime(now) #当地时间
time.struct_time(tm_year=2019, tm_mon=7, tm_mday=26, tm_hour=9, tm_min=17, tm_sec=34, tm_wday=4, tm_yday=207, tm_isdst=0)
结构化时间到时间戳的转化
- time.mktime(结构化时间)
>>> import time
>>> tp_struct = time.localtime()
>>> time.mktime(tp_struct)
1564104160.0
结构化时间到字符串时间的转化
- time.strftime(format,[t])
>>> import time
>>> tp_struct = time.localtime()
>>> time.strftime("%Y-%m-%d %X",tp_struct)
'2019-07-26 09:25:49'
字符串时间到结构化时间的转化
- time.strptime(时间字符串,字符串对应格式)
>>> import time
>>> time.strptime("2019-07-26","%Y-%m-%d")
time.struct_time(tm_year=2019, tm_mon=7, tm_mday=26, tm_hour=0, tm_min=0, tm_sec=0, tm_wday=4, tm_yday=207, tm_isdst=-1)
>>> time.strptime("2019/07/26","%Y/%m/%d")
time.struct_time(tm_year=2019, tm_mon=7, tm_mday=26, tm_hour=0, tm_min=0, tm_sec=0, tm_wday=4, tm_yday=207, tm_isdst=-1)
结构化时间到字符串时间的转化(国际化)
- time.asctime(结构化时间)
>>> import time
>>> tp_struct = time.localtime()
>>> time.asctime(tp_struct)
'Fri Jul 26 09:48:50 2019'
>>>
时间戳和字符串的转化(国际化)
- time.ctime()
>>> import time
>>> time.ctime()
'Fri Jul 26 09:51:35 2019'
四、datetime模块
相比time来说,datetime模块接口更直观,更容易调用
方法(类) | 描述 |
---|---|
datetime.date | 表示日期,常用属性year,month,day |
datetime.time | 表示时间,常用属性hour,minute,second,microsecond |
datetime.datetime | 表示日期 |
datetime.timedelta | 表示时间间隔 |
datetime.tzinfo | 与时间有关的信息 |
>>> import datetime
>>> datetime.datetime.now()
datetime.datetime(2019, 7, 26, 10, 3, 9, 268699)
>>> print(datetime.datetime.now())
2019-07-26 10:03:22.407957
>>> print(datetime.datetime.now().date())
2019-07-26
>>> print(datetime.datetime.now()+datetime.timedelta(-1)) #当前时间减1天
2019-07-25 10:11:28.666545
>>> print(datetime.datetime.now()+datetime.timedelta(hours = 1)) #当前时间加1小时
2019-07-26 11:11:54.810438
五、sys模块
sys模块是与Python解释器交互的一个接口
处理命令行参数
在解释器启动后,argv列表包含了传递脚本的所有参数,列表的第一个函数就是文件名
import sys
print("Script name is:",sys.argv[0])
if len(sys.argv) >1:
print("There are ",len(sys.argv)-1,"arguments:")
for i in sys.argv[1:]:
print(i)
else:
print("There are no arguments")
运行
D:\PycharmProjects\untitled1>python test190726.py a b c
Script name is: test190726.py
There are 3 arguments:
a
b
c
import sys
print(sys.byteorder) #显示本地字节序的指示符。
print(sys.copyright) #显示python解释器有关的版权信息
print(sys.executable) #显示python解释器在磁盘的存储路径。
print(sys.getfilesystemencoding()) #显示当前系统上保存文件所用的字符集。
print(sys.maxsize) #显示python整数支持的最大值
print(sys.platform) #显示python解释器所在平台
print(sys.version) #显示当前python解释器的版本信息
print(sys.winver) #返回当前python解释器的主版本号
六、序列化模块
序列化:将一个对象从内存中转化为可储存(字符串类型)或者可传输(bytes)类型的过程。python中加pickling
- 持久化数据类型
- 跨平台交互使用
- 使程序更易维护
数据结构--------序列化---------->str/bytes
str/bytes-------反序列化--------->数据结构
6.1 json
json格式在各个语言中都可以通用的序列化格式。在json中,所有的字符串必须为双引号
json类型 | python类型 |
---|---|
{ } | dict |
[ ] | list |
“string” | str |
1234.56 | int/float |
true/false | True/False |
null | None |
json优缺点
- 优点:所有的数据类型是各语言通用的
- 缺点:
- json只支持比较少的数据类型
- 对数据类型的约束十分严格
- 字典中的key必须是字符串
- json只支持字符串,列表,字典,数值和布尔值
查看json的方法和属性
>>> import json
>>> dir(json)
['JSONDecodeError', 'JSONDecoder', 'JSONEncoder', '__all__', '__author__', '__builtins__', '__cached__', '__doc__', '__file__', '__loader__', '__name__', '__package__', '__path__', '__spec__', '__version__', '_default_decoder', '_default_encoder', 'codecs', 'decoder', 'detect_encoding', 'dump', 'dumps', 'encoder', 'load', 'loads', 'scanner']
>>>
四个功能
- dumps
- dump
- loads
- load
>>> import json
#序列化
>>> dic = {"name":"City College","age":20,"type":"University"}
>>> sr_dic = json.dumps(dic) #序列化,将字典转化为一个字符串
>>> type(sr_dic)
<class 'str'>
>>> print(sr_dic)
{"name": "City College", "age": 20, "type": "University"}
>>> dic
{'name': 'City College', 'age': 20, 'type': 'University'}
>>> sr_dic
'{"name": "City College", "age": 20, "type": "University"}'
>>>
#反序列化
>>> dic_2 = json.loads(sr_dic)
>>> type(dic_2)
<class 'dict'>
>>> dic_2
{'name': 'City College', 'age': 20, 'type': 'University'}
如果是元组,序列化时强转为列表;若元组作为字典的键,序列化报错
如果把数据类型直接序列化写入文件中,可以用dump和load方法
import json
dic = {"name":"City College","age":20,"type":"University",2:6}
with open("dump_json","w") as f:
json.dump(dic,f) #dump方法可以接收一个文件句柄。直接将字典-->字符串,写入文件
with open("dump_json") as f:
ret = json.load(f)
print((ret,type(ret)))
import json
dic = {"name":"City College","age":20,"type":"University",2:6}
dic2 = {"city":"Hangzhou","history":5000}
with open("dump_json","w") as f:
str_dic1 = json.dumps(dic)
str_dic2 = json.dumps(dic2)
f.write(str_dic1+'\n')
f.write(str_dic2+'\n')
with open("dump_json") as f:
for i in f:
ret = json.loads(i)
print(ret)
6.2 pickle
只用于python。
内存中结构化的数据<—>格式pickle<—>bytes类型<—>保存在文件或基于网络传输
优缺点
- 优点
- 支持python中的几乎所有类型
- pickle会把数据类型序列化为bytes类型
- 缺点
- 只支持python
四个功能
- 序列化
- dump
- dumps
- 反序列化
- load
- loads
import pickle
dic = {"name":"City College","age":20,"type":"University",2:6}
dic_b = pickle.dumps(dic)
print(type(dic_b)) #<class 'bytes'>
dic_d = pickle.loads(dic_b)
print(type(dic_d)) #<class 'dict'>
import pickle
dic = {"name":"City College","age":20,"type":"University",2:6}
with open("dump_pickle","wb") as f:
pickle.dump(dic,f)
with open("dump_pickle","rb") as f:
ret = pickle.load(f)
print(ret)
七、包(pockage)
包:包是通过使用".模块名"来组织python模块名称空间的方式。具体而言,包就是一个包含__init__.py
文件的文件夹
目的:用文件夹将文件/模块组织起来
注意:
py3,即使包中没有
__init__.py
也可以使用py2,如果没有会报错
创建包的目的不是为了运行,而是为了被导入使用。包的本质依然还是模块
- 使用时,import导入,导入带点的,点的最左边一定是包名
- import导入文件时,产生名称空间的名字源于文件。import 包时,名字空间同样源于文件(包),导入包的本质就是导入
__init__.py
实例
- 建立如下结构:
school tree
├── api
│ ├── __init__.py
│ ├── students.py
│ └── versions.py
├── cmd
│ ├── __init__.py
│ └── manage.py
├── db
│ ├── __init__.py
│ └── models.py
└── __init__.py
- 写入如下的代码:
#students.py
def get():
print("from studentd.py")
#versions.py
def create_resoource(conf):
print("from versions.py",conf)
#manage.py
def main():
print("from manage.py")
#models.py
def register_models(engine):
print("from models.py",engine)
- 执行:
import school.db.models
school.db.models.register_models("MySQL")
#from models.py MySQL
from school.cmd import manage
manage.main()
#from manage.py
from school.cmd.manage import main
main()
#from manage.py
import school
school.cmd.manage.main()
#AttributeError: module 'school' has no attribute 'cmd'
#单独导入包时,不会导入该包中所包含的所有子模块
from school import cmd.manage
main()
#SyntaxError: invalid syntax
#.要放在from的后面
要先单独导入包运行子模块,要在__init__.py
中加入调用模块的语句
#school下__init__.py
from . import cmd
#cmd下__init__.py
from . import manage
运行
import school
school.cmd.manage.main()
#from manage.py
在school/api/version.py 中导入school/cmd/manage.py
#version.py
from school.cmd import manage #绝对导入
'''或者
from ..cmd import manage #相对导入
'''
#test.py
from school.api import versions
versions.manage.main()
#from manage.py