Python基础(7)- python各类模块、正则表达式、元字符、异常处理

来源:互联网 发布:vc6.0连接sql数据库 编辑:程序博客网 时间:2024/06/06 01:47

一、时间模块

tips:
在python中for循环’不’能开辟自己的作用域
在python中if…else…’不’能开辟自己的作用域

☆在python中只有函数、类、模块这三个东西可以开辟自己独立的作用域!

什么是模块?
模块就是.py文件

一、时间模块
import time
time.sleep(10)

时间表示形式
1、时间戳
time.time()

2、时间字符串
time.strftime(‘%Y-%m-%d %X’)

3、时间元组-结构化时间
time.localtime()
返回的是一个对象,可以用.调用其中的对象

几种时间的互相转换:结构化时间、时间戳、字符串时间
结构化时间——mktime——>时间戳

时间戳——localtime/gmtime——>结构化时间

结构化时间——strftime——>字符串时间

字符串时间——strptime——>结构化时间

一 时间戳<---->结构化时间: localtime/gmtime mktime

time.localtime(3600*24)
time.gmtime(3600*24)
time.mktime(time.localtime())
字符串时间<---->结构化时间: strftime/strptime
time.strftime(“%Y-%m-%d %X”, time.localtime())
time.strptime(“2017-03-16”,”%Y-%m-%d”)

4、

time.asctime(time.localtime(312343423))
‘Sun Nov 25 10:03:43 1979’
time.ctime(312343423)
‘Sun Nov 25 10:03:43 1979’

5、sleep效果等同于I/O(例如input,f.read)
线程推迟指定的时间运行,单位为秒。

二、random模块

随机数模块
1、0-1的浮点型数字
random.random()

2、random.randint(1,5) # 大于等于1且小于等于5之间的整数,[1,5]

3、random.randrange(1,3) # 大于等于1且小于3之间的整数,[1,3)

4、random.choice([1,’23’,[4,5]]) # #1或者23或者[4,5]

5、random.sample([1,’23’,[4,5]],n) # #列表元素任意n个组合

6、random.uniform(1,3) #大于1小于3的小数

7、random.shuffle(item) # 打乱次序
例子:

item=[1,3,5,7,9]
random.shuffle(item) # 打乱次序
item
[5, 1, 3, 7, 9]

8、random.shuffle(item)
item
[5, 9, 7, 1, 3]

hashlib模块:Python的hashlib提供了常见的摘要算法,如MD5,SHA1等等。

MD5摘要算法:
import hashlib

md5 = hashlib.md5()
md5.update(‘how to use md5 in python hashlib?’.encode(“utf8”))
print md5.hexdigest()

计算结果如下:
d26a53750bc40b38b65a520292f69306

三、os模块

os模块是与操作系统交互的一个接口
os.getcwd() 获取当前工作目录,即当前python脚本工作的目录路径
os.chdir(“dirname”) 改变当前脚本工作目录;相当于shell下cd
os.curdir 返回当前目录: (‘.’)
os.pardir 获取当前目录的父目录字符串名:(‘..’)
os.makedirs(‘dirname1/dirname2’) 可生成多层递归目录
os.removedirs(‘dirname1’) 若目录为空,则删除,并递归到上一级目录,如若也为空,则删除,依此类推
os.mkdir(‘dirname’) 生成单级目录;相当于shell中mkdir dirname
os.rmdir(‘dirname’) 删除单级空目录,若目录不为空则无法删除,报错;相当于shell中rmdir dirname
os.listdir(‘dirname’) 列出指定目录下的所有文件和子目录,包括隐藏文件,并以列表方式打印
os.remove() 删除一个文件
os.rename(“oldname”,”newname”) 重命名文件/目录
os.stat(‘path/filename’) 获取文件/目录信息
os.sep 输出操作系统特定的路径分隔符,win下为”\”,Linux下为”/”
os.linesep 输出当前平台使用的行终止符,win下为”\t\n”,Linux下为”\n”
os.pathsep 输出用于分割文件路径的字符串 win下为;,Linux下为:
os.name 输出字符串指示当前使用平台。win->’nt’; Linux->’posix’
os.system(“bash command”) 运行shell命令,直接显示
os.environ 获取系统环境变量
os.path.abspath(path) 返回path规范化的绝对路径
os.path.split(path) 将path分割成目录和文件名二元组返回
os.path.dirname(path) 返回path的目录。其实就是os.path.split(path)的第一个元素
os.path.basename(path) 返回path最后的文件名。如何path以/或\结尾,那么就会返回空值。即os.path.split(path)的第二个元素
os.path.exists(path) 如果path存在,返回True;如果path不存在,返回False
os.path.isabs(path) 如果path是绝对路径,返回True
os.path.isfile(path) 如果path是一个存在的文件,返回True。否则返回False
os.path.isdir(path) 如果path是一个存在的目录,则返回True。否则返回False
os.path.join(path1[, path2[, …]]) 将多个路径组合后返回,第一个绝对路径之前的参数将被忽略
os.path.getatime(path) 返回path所指向的文件或者目录的最后访问时间
os.path.getmtime(path) 返回path所指向的文件或者目录的最后修改时间
os.path.getsize(path) 返回path的大小

四、sys模块:主要和python解释器打交道

sys.argv 命令行参数List,第一个元素是程序本身路径
sys.exit(n) 退出程序,正常退出时exit(0)
sys.version 获取Python解释程序的版本信息
sys.maxint 最大的Int值
sys.path 返回模块的搜索路径,初始化时使用PYTHONPATH环境变量的值
sys.platform 返回操作系统平台名称

五、logging模块

import logging
logging.debug(‘debug message’)
logging.info(‘info message’)
logging.warning(‘warning message’)
logging.error(‘error message’)
logging.critical(‘critical message’)

logging的等级优先级:
默认情况下Python的logging模块将日志打印到了标准输出中,且只显示了大于等于WARNING级别的日志,
这说明默认的日志级别设置为WARNING(日志级别等级CRITICAL > ERROR > WARNING > INFO > DEBUG),
默认的日志格式为日志级别:Logger名称:用户输出消息。

配置日志的两种方式:
1、config函数

灵活配置日志级别,日志格式,输出位置:
import logging
logging.basicConfig(level=logging.DEBUG,
format=’%(asctime)s %(filename)s[line:%(lineno)d] %(levelname)s %(message)s’,
datefmt=’%a, %d %b %Y %H:%M:%S’,
filename=’/tmp/test.log’,
filemode=’w’)

logging.debug(‘debug message’)
logging.info(‘info message’)
logging.warning(‘warning message’)
logging.error(‘error message’)
logging.critical(‘critical message’)

①format配置参数:
logging.basicConfig()函数中可通过具体参数来更改logging模块默认行为,可用参数有:
filename:用指定的文件名创建FiledHandler,这样日志会被存储在指定的文件中。
filemode:文件打开方式,在指定了filename时使用这个参数,默认值为“a”还可指定为“w”。
format:指定handler使用的日志显示格式。
datefmt:指定日期时间格式。
level:设置rootlogger(后边会讲解具体概念)的日志级别
stream:用指定的stream创建StreamHandler。可以指定输出到sys.stderr,sys.stdout或者文件(f=open(‘test.log’,’w’)),
默认为sys.stderr。若同时列出了filename和stream两个参数,则stream参数会被忽略。
format参数中可能用到的格式化串:
%(name)s Logger的名字
%(levelno)s 数字形式的日志级别
%(levelname)s 文本形式的日志级别
%(pathname)s 调用日志输出函数的模块的完整路径名,可能没有
%(filename)s 调用日志输出函数的模块的文件名
%(module)s 调用日志输出函数的模块名
%(funcName)s 调用日志输出函数的函数名
%(lineno)d 调用日志输出函数的语句所在的代码行
%(created)f 当前时间,用UNIX标准的表示时间的浮 点数表示
%(relativeCreated)d 输出日志信息时的,自Logger创建以 来的毫秒数
%(asctime)s 字符串形式的当前时间。默认格式是 “2003-07-08 16:49:45,896”。逗号后面的是毫秒
%(thread)d 线程ID。可能没有
%(threadName)s 线程名。可能没有
%(process)d 进程ID。可能没有
%(message)s用户输出的消息

2、logger-建议用这个,因为可以设置复杂情况的日志☆
logger对象配置

import logging
logger = logging.getLogger()

创建一个handler,用于写入日志文件
fh = logging.FileHandler(‘test.log’)

再创建一个handler,用于输出到控制台
ch = logging.StreamHandler()

formatter = logging.Formatter(‘%(asctime)s - %(name)s - %(levelname)s - %(message)s’)
fh.setFormatter(formatter)
ch.setFormatter(formatter)
logger.addHandler(fh) #logger对象可以添加多个fh和ch对象
logger.addHandler(ch)
logger.debug(‘logger debug message’)
logger.info(‘logger info message’)
logger.warning(‘logger warning message’)
logger.error(‘logger error message’)
logger.critical(‘logger critical message’)

logging库提供了多个组件:Logger、Handler、Filter、Formatter。
Logger对象提供应用程序可直接使用的接口,Handler发送日志到适当的目的地,Filter提供了过滤日志信息的方法,Formatter指定日志显示格式。
另外,可以通过:logger.setLevel(logging.Debug)设置级别,当然,也可以通过
fh.setLevel(logging.Debug)单对文件流设置某个级别。

六、json模块

之前我们学习过用eval内置方法可以将一个字符串转成python对象,不过,eval方法是有局限性的,对于普通的数据类型,
json.loads和eval都能用,但遇到特殊类型的时候,eval就不管用了,所以eval的重点还是通常用来执行一个字符串表达式,并返回表达式的值。

什么是序列化?
我们把对象(变量)从内存中变成可存储或传输的过程称之为序列化,在Python中叫pickling,
在其他语言中也被称之为serialization,marshalling,flattening等等,都是一个意思。
序列化之后,就可以把序列化后的内容写入磁盘,或者通过网络传输到别的机器上。
反过来,把变量内容从序列化的对象重新读到内存里称之为反序列化,即unpickling。

json模块
如果我们要在不同的编程语言之间传递对象,就必须把对象序列化为标准格式,比如XML,但更好的方法是序列化为JSON,
因为JSON表示出来就是一个字符串,可以被所有语言读取,也可以方便地存储到磁盘或者通过网络传输。
JSON不仅是标准格式,并且比XML更快,而且可以直接在Web页面中读取,非常方便。

例子:
import json

d = {“北京”:[“西城”,”东城”],”上海”:[“浦东新区”,”静安区”]}

序列化
s = json.dumps(d) #将字典d转化为json字符串

反序列化
json.loads(data) #将json字符串转化为字典

tips:
如果在文件中存储的字符格式符合json的格式标准,就可以在python程序中直接loads从而从文件中直接取得字符串并且反序列为相应字符格式

json的键值对格式中的key必须用”“双引号

七、pickle模块与正则、正则表达式与元字符

pickle只能在python语言间进行数据序列化,可以序列化各种字符类型

使用方法与json完全一样,同样具有dumps与loads方法

正则的用途:对字符串做模糊匹配
正则元字符(有特殊功能的字符叫做元字符):11个

import re

re.findall() #找到在所有的匹配元素,返回列表

1、通配符·
可以匹配任何一个除换行符以外的符号

2、* [0,+∞]

3、+ [1,+∞]

4、? [0,1]

5、{} {n,m}

6、字符集 []
匹配[]里面的一个字符

注意:
①、\d 效果等同于 [0-9]
②^在[]中则表示‘取反’
③* + .等元字符在[]中都是普通字符,而- ^ \在[]中还是有特殊意义的

7、开始位置匹配 ^

8、结尾位置匹配 $

9、分组 ()
如果有分组的情况下,系统默认显示分组内的内容,而不会显示出所有的匹配内容,如果想取消分组的优先级,则要在分组内加上(?:)

10、转义 \
①后面加一个元字符时期编程普通符号 例如:. *
②将一些普通符号变成特殊符号 例如:\w \d

\d 匹配任何十进制数;它相当于类 [0-9]。
\D 匹配任何非数字字符;它相当于类 [^0-9]。
\s 匹配任何空白字符;它相当于类 [ \t\n\r\f\v]。
\S 匹配任何非空白字符;它相当于类 [^ \t\n\r\f\v]。
\w 匹配任何字母数字字符;它相当于类 [a-zA-Z0-9_]。
\W 匹配任何非字母数字字符;它相当于类 [^a-zA-Z0-9_]
\b 匹配一个特殊字符边界,比如空格 ,&,#等

八、正则表达式方法

import re
1、re.findall()
找到在所有的匹配元素,返回列表

2、re.finditer()
找到在所有的匹配元素,返回可迭代对象

3、re.search()
只匹配第一个结果
直接search是一个可迭代的对象,之后再调用该对象的group()方法得到对应匹配的结果

4、re.match()
只在字符串开始的位置匹配

5、re.split()
分割

6、re.sub()
替换

7、re.compile
定义规则

补充①:正则元字符——命名分组 ()

import rere.findall(r"(?P<author>\w+)\\articles\\(?P<id>\d{4})","yuan\articles\1234")其中?P<name>部分就是为规则命名为规则命名之后,可以在search()方法中group()方法里调用名称res = re.search(r"(?P<author>\w+)\\articles\\(?P<id>\d{4})","yuan\articles\1234")print(res.group('author'))

补充②:贪婪匹配(系统默认的匹配方式)
非贪婪匹配:最后加?

九、异常处理

常用异常:
AttributeError 试图访问一个对象没有的树形,比如foo.x,但是foo没有属性x
IOError 输入/输出异常;基本上是无法打开文件
ImportError 无法引入模块或包;基本上是路径问题或名称错误
IndentationError 语法错误(的子类) ;代码没有正确对齐
IndexError 下标索引超出序列边界,比如当x只有三个元素,却试图访问x[5]
KeyError 试图访问字典里不存在的键
KeyboardInterrupt Ctrl+C被按下
NameError 使用一个还未被赋予对象的变量
SyntaxError Python代码非法,代码不能编译(个人认为这是语法错误,写错了)
TypeError 传入对象类型与要求的不符合
UnboundLocalError 试图访问一个还未被设置的局部变量,基本上是由于另有一个同名的全局变量,
导致你以为正在访问它
ValueError 传入一个调用者不期望的值,即使值的类型是正确的

什么是异常处理?
python解释器检测到错误,触发异常(也允许程序员自己触发异常)
程序员编写特定的代码,专门用来捕捉这个异常(这段代码与程序逻辑无关,与异常处理有关)
如果捕捉成功则进入另外一个处理分支,执行你为其定制的逻辑,使程序不会崩溃,这就是异常处理

为何要进行异常处理?
python解析器去执行程序,检测到了一个错误时,触发异常,异常触发后且没被处理的情况下,程序就在当前异常处终止,
后面的代码不会运行,谁会去用一个运行着突然就崩溃的软件。
所以你必须提供一种异常处理机制来增强你程序的健壮性与容错性

如何进行异常处理?
一:使用if判断式
二:python为每一种异常定制了一个类型,然后提供了一种特定的语法结构用来进行异常处理
part1:基本语法
try:
被检测的代码块
except 异常类型:
try中一旦检测到异常,就执行这个位置的逻辑

part2:异常类只能用来处理指定的异常情况,如果非指定异常则无法处理。
part3:多分支
part4:万能异常 在python的异常中,有一个万能异常:Exception,他可以捕获任意异常
part5:异常的其他机构

s1 = 'hello'try:    int(s1)except IndexError as e:    print(e)except KeyError as e:    print(e)except ValueError as e:    print(e)#except Exception as e:#    print(e)else:    print('try内代码块没有异常则执行我')finally:    print('无论异常与否,都会执行该模块,通常是进行清理工作')

part6:主动触发异常

try:    raise TypeError('类型错误')except Exception as e:    print(e)

part7:自定义异常

class EgonException(BaseException):    def __init__(self,msg):        self.msg=msg    def __str__(self):        return self.msgtry:    raise EgonException('类型错误')except EgonException as e:    print(e)

part8:断言
assert 条件
assert 1 == 1
assert 1 == 2

part9:try..except的方式比较if的方式的好处
使用try..except的方式
1:把错误处理和真正的工作分开来
2:代码更易组织,更清晰,复杂的工作任务更容易实现;
3:毫无疑问,更安全了,不至于由于一些小的疏忽而使程序意外崩溃了

什么时候用异常处理?
有的同学会这么想,学完了异常处理后,好强大,我要为我的每一段程序都加上try…except,干毛线去思考它会不会有逻辑错误啊,
这样就很好啊,多省脑细胞===》2B青年欢乐多
try…except应该尽量少用,因为它本身就是你附加给你的程序的一种异常处理的逻辑,与你的主要的工作是没有关系的
这种东西加的多了,会导致你的代码可读性变差
而且异常处理本就不是你2b逻辑的擦屁股纸,只有在有些异常无法预知的情况下,才应该加上try…except,其他的逻辑错误应该尽量修正

十、模块导入

导入的两种方式:
1、import
①第一件事:创建名称空间
②第二件事:基于刚刚创建的名称空间执行.py文件
③第三件事:创建模块名,指向刚刚创建的名称空间

2、from……import……
与import的区别就是不用加前缀来调用

3、查找模块顺序
内存中已经加载的模块->内置模块->sys.path路径中包含的模块
☆需要特别注意的是:我们自定义的模块名不应该与系统内置模块重名。虽然每次都说,但是仍然会有人不停的犯错。

4、编译python文件
编译python文件
.pyc文件—字节码文件—>缓存—>为了加速加载
只有导入模块的时候会产生.pyc文件

提示:
1.模块名区分大小写,foo.py与FOO.py代表的是两个模块
2.你可以使用-O或者-OO转换python命令来减少编译模块的大小
-O转换会帮你去掉assert语句
-OO转换会帮你去掉assert语句和doc文档字符串
由于一些程序可能依赖于assert语句或文档字符串,你应该在在确认需要的情况下使用这些选项。
3.在速度上从.pyc文件中读指令来执行不会比从.py文件中读指令执行更快,只有在模块被加载时,.pyc文件才是更快的
4.只有使用import语句是才将文件自动编译为.pyc文件,在命令行或标准输入中指定运行脚本则不会生成这类文件,
因而我们可以使用compieall模块为一个目录中的所有模块创建.pyc文件
模块可以作为一个脚本(使用python -m compileall)编译Python源
python -m compileall /module_directory 递归着编译
如果使用python -O -m compileall /module_directory -l则只一层
命令行里使用compile()函数时,自动使用python -O -m compileall
详见:https://docs.python.org/3/library/compileall.html#module-compileall

十一、包导入

包:包含__init__.py文件的文件夹
包是一种通过使用‘.模块名’来组织python模块名称空间的方式。
1. 无论是import形式还是from…import形式,凡是在导入语句中(而不是在使用时)遇到带点的,都要第一时间提高警觉:这是关于包才有的导入语法
2. 包是目录级的(文件夹级),文件夹是用来组成py文件(包的本质就是一个包含__init__.py文件的目录)
3. import导入文件时,产生名称空间中的名字来源于文件,import 包,产生的名称空间的名字同样来源于文件,即包下的__init__.py,导入包本质就是在导入该文件

导入包本质就是导入包下面的__init__.py文件,例:from 包名 import *是代表导入包下__init__.py中__all__ = [文件名1,文件名2]的文件1和文件2

特别需要注意的是:可以用import导入内置或者第三方模块(已经在sys.path中),
但是要绝对避免使用import来导入自定义包的子模块(没有在sys.path中),应该使用from… import …的绝对或者相对导入,且包的相对导入只能用from的形式。

绝对导入与相对导入
在glance/api/version.py
绝对导入
from glance.cmd import manage
manage.main()
相对导入
from ..cmd import manage
manage.main()

阅读全文
0 0