模块就是其他语言的类库,分三种:内置模块、自定义模块、第三方模块
模块要先导入后使用
模块的作用:代码归类
导入模块:
import commons commons.login() #执行commons模块的login()方法 import commons as obj #导入模块并设置别名 obj.login() obj = _import_("commons") #以字符串导入模块 obj.login() obj = _import_("lib.commons", fromlist=True) #默认只导入lib,加上fromlist=True参数则导入lib.commons
能被导入模块的位置:
import sys print(sys.path)
把当前py文件的路径加入sys.path
#__file__ 当前py文件所在路径 print(__file__) import os #os.path.abspath() 获取某个文件的绝对路径 #os.path.dirname() 某文件的上级目录 print(os.path.abspath(__file__)) #当前py文件的绝对路径 print(os.path.dirname(os.path.abspath(__file__))) #当前py文件的上一级路径 import sys,os sys.path.append(os.path.dirname(os.path.abspath(__file__))) #把当前py文件的上一级路径加入sys.path
在Linux或Windows中输入命令
import os os.system("ps -ef") #在linux中调用命令 res = os.system("ifconfig") #命令结果赋值给变量 print(res) #ifconfig执行成功,res=0 res = os.popen("ifconfig").read() #把命令执行过程赋值给变量 print(res)
from调用模块
from sys import path #直接调用模块内功能 print(path) from lib import commons #文件夹下调用模块 commons.xx #lib和src文件夹下都有commons模块 from lib import commons as lib_commons from src import commons as src_commons lib_commons.xx src_commons.xx
第三方模块安装
requests模块
pip3安装
pip3 install requests
源码安装
python3 setup.py install
pip使用 http://www.ttlsa.com/python/how-to-install-and-use-pip-ttlsa/
模块中的特殊变量
#__file__ 当前py所在路径 #__package__ 当前py文件所在的包 print(__package__)
#__name__ 只有执行当前文件时,当前文件的特殊变量__name__ == "__main__" cat S1.py def run1(): print('run1') def run2(): print('run2') if __name__ == "__main__": run1() run2() cat S2.py import S1 #import S1的时候,S1的__name__不是"__main__",所用不会执行run1(),只执行run2()
==========================================================================================
sys模块
sys.argv #命令行参数List,第一个元素是程序本身路径 sys.exit(n) #退出程序,正常退出时exit(0) sys.version #获取Python解释程序的版本信息 sys.maxint #最大的Int值 sys.path #返回模块的搜索路径,初始化时使用PYTHONPATH环境变量的值 sys.platform #返回操作系统平台名称
os模块
os.getcwd() #获取当前工作目录,即当前python脚本工作的目录路径 os.chdir("dirname") #改变当前脚本工作目录;相当于shell下cd os.curdir #返回当前目录: ('.') os.pardir #获取当前目录的父目录字符串名:('..') os.makedirs('dir1/dir2') #可生成多层递归目录 os.removedirs('dirname1') #若目录为空,则删除,并递归到上一级目录,如若也为空,则删除,依此类推 os.mkdir('dirname') #生成单级目录;相当于shell中mkdir dirname os.rmdir('dirname') #删除单级空目录,若目录不为空则无法删除,报错;相当于shell中rmdir dirname os.listdir('dirname') #列出指定目录下的所有文件和子目录,包括隐藏文件,并以列表方式打印 os.remove() #删除一个文件 os.rename("oldname","new") #重命名文件/目录 os.stat('path/filename') #获取文件/目录信息 os.sep #操作系统特定的路径分隔符,win下为"\",Linux下为"/" os.linesep #当前平台使用的行终止符,win下为" ",Linux下为" " os.pathsep #用于分割文件路径的字符串 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所指向的文件或者目录的最后修改时间
系统命令subprocess模块
#call 执行命令,返回状态码 ret = subprocess.call(["ls", "-l"], shell=False) ret = subprocess.call("ls -l", shell=True) #check_call 执行命令,如果执行状态码是 0 ,则返回0,否则抛异常 subprocess.check_call(["ls", "-l"]) subprocess.check_call("exit 1", shell=True) #check_output 执行命令,如果状态码是 0 ,则返回执行结果,否则抛异常 subprocess.check_output(["echo", "Hello World!"]) subprocess.check_output("exit 1", shell=True)
#subprocess.Popen(...) 用于执行复杂的系统命令 ret1 = subprocess.Popen(["mkdir","t1"]) ret2 = subprocess.Popen("mkdir t2", shell=True) obj = subprocess.Popen("mkdir t3", shell=True, cwd='/home/dev')
import subprocess obj = subprocess.Popen(["python"], stdin=subprocess.PIPE,
stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True) #标准输入、标准输出、标准错误都是管道。换行符统一为 obj.stdin.write("print('hello world') ") obj.stdin.write("print(2)") obj.stdin.close() cmd_out = obj.stdout.read() obj.stdout.close() cmd_error = obj.stderr.read() obj.stderr.close() print(cmd_out) print(cmd_error)
import subprocess obj = subprocess.Popen(["python"], stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True) obj.stdin.write("print(1) ") obj.stdin.write("print(2)") out_error_list = obj.communicate() #标准输出和标准错误都输入到列表 print(out_error_list)
import subprocess obj = subprocess.Popen(["python"], stdin=subprocess.PIPE,
stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True) out_error_list = obj.communicate('print("hello")') print(out_error_list)
正则表达式re模块
'.' 默认匹配除 之外的任意一个字符,若指定flag DOTALL,则匹配任意字符,包括换行 '^' 匹配字符开头,若指定flags MULTILINE,这种也可以匹配上(r"^a"," abc eee",flags=re.MULTILINE) '$' 匹配字符结尾,或e.search("foo$","bfoo sdfsf",flags=re.MULTILINE).group()也可以 '*' 匹配*号前的字符0次或多次,re.findall("ab*","cabb3abcbbac") 结果为['abb', 'ab', 'a'] '+' 匹配前一个字符1次或多次,re.findall("ab+","ab+cd+abb+bba") 结果['ab', 'abb'] '?' 匹配前一个字符1次或0次 '{m}' 匹配前一个字符m次 '{n,m}' 匹配前一个字符n到m次,re.findall("ab{1,3}","abb abc abbcbbb") 结果'abb', 'ab', 'abb'] '|' 匹配|左或|右的字符,re.search("abc|ABC","ABCBabcCD").group() 结果'ABC' '(...)' 分组匹配,re.search("(abc){2}a(123|456)c", "abcabca456c").group() 结果 abcabca456c 'A' 只从字符开头匹配,re.search("Aabc","alexabc") 是匹配不到的 '' 匹配字符结尾,同$ 'd' 匹配数字0-9 'D' 匹配非数字 'w' 匹配[A-Za-z0-9] 'W' 匹配非[A-Za-z0-9] 's' 匹配空白字符、 、 、 , re.search("s+","ab c1 3").group() 结果 ' ' '(?P<name>...)' 分组匹配 re.search("(?P<province>[0-9]{4})(?P<city>[0-9]{2})(?P<birthday>[0-9]{4})","371481199306143242").groupdict("city") 结果{'province': '3714', 'city': '81', 'birthday': '1993'}
re.match(pattern, string, flags=0) 从头开始匹配 re.search(pattern, string, flags=0) 匹配包含 re.findall(pattern, string, flags=0) 获取非重复的匹配列表;如果有一个组则以列表形式返回,且每一个匹配均是字符串;如果模型中有多个组,则以列表形式返回,且每一个匹配均是元组 re.split(pattern, string, maxsplit=0, flags=0) 以匹配到的字符当做列表分隔符 re.sub(pattern, repl, string, count=0, flags=0) 替换匹配成功的指定位置字符串 # pattern: 正则模型 # string : 要匹配的字符串 # repl : 要替换的字符串或可执行对象 # count : 指定匹配个数 # maxsplit:指定分割个数 # falgs : 匹配模式 X VERBOSE Ignore whitespace and comments for nicer looking RE's. I IGNORECASE Perform case-insensitive matching. M MULTILINE "^" matches the beginning of lines (after a newline) as well as the string. "$" matches the end of lines (before a newline) as well as the end of the string. S DOTALL "." matches any character at all, including the newline. A ASCII For string patterns, make w, W, , B, d, D match the corresponding ASCII character categories (rather than the whole Unicode categories, which is the default). For bytes patterns, this flag is the only available behaviour and needn't be specified. L LOCALE Make w, W, , B, dependent on the current locale. U UNICODE For compatibility only. Ignored for string patterns (it is the default), and forbidden for bytes patterns.
configparser
用于处理特定格式的文件,其本质上是利用open来操作文件。
# 特定格式如下 [section1] # 节点 k1 = v1 # 值 k2:v2 # 值 [section2] # 节点 k1 = v1 # 值
import configparser config = configparser.ConfigParser() #在内存中打开一个对象 config.read('tample.ini', encoding='utf-8') #读tample.ini文件 ret = config.sections() #获取所有节点 print(ret) ret = config.items('section1') #获取指定节点下所有的键值对 print(ret) ret = config.options('section1') #获取指定节点下所有的建 print(ret) v = config.get('section1', 'k1') #获取指定节点下指定key的值,默认str格式 # v = config.getint('section1', 'k1') #key值为int值 # v = config.getfloat('section1', 'k1') #key值为float值 # v = config.getboolean('section1', 'k1') #key值为布尔值 print(v) has_sec = config.has_section('section1') #检查节点 print(has_sec) config.add_section("SEC_1") #添加节点 config.write(open('tample.ini', 'w')) #从内存写入文件 config.remove_section("SEC_1") #删除节点 config.write(open('tample.ini', 'w')) has_opt = config.has_option('section1', 'k1') #检查指定节点下的键值对 print(has_opt) config.remove_option('section1', 'k1') #删除键值对 config.write(open('tample.ini', 'w')) config.set('section1', 'k10', "123") #删除键值对 config.write(open('tample.ini', 'w'))
序列化相关
1.json 多语言通用,适用于跨语言的简单数据类型
import json dic={"k1":"v1"} print(dic,type(dic)) ret=json.dumps(dic) #将python的基本数据类型转换成字符串形式 print(ret,type(ret)) dic=json.loads(ret) #将字符串转换成基本数据类型,要使用双引号 print(dic,type(dic)) json.dump(dic,open("db","w")) #先序列化,然后写入文件 dic=json.load(open("db","r")) #读取文件然后反序列化 print(type(dic),dic)
2.pickle python专用,适用于python所有数据类型(不同python版本件不一定通用)
import pickle li=[11,22,33] r=pickle.dumps(li) #序列化成python的bytes形式 print(r) ret=pickle.loads(r) #反序列化,支持包括复杂数据类型在内的任何数据类型 print(ret) pickle.dump(li,open("db","wb")) #序列化然后写入文件 li=pickle.load(open("db","rb")) #读取文件然后反序列化 print(li,type(li))
XML模块
import xml.etree.ElementTree as ET from xml.etree import ElementTree as ET
时间模块
time #常用取时间戳
import time print(time.time()) #时间戳,从1970年开始到现在的时间(秒) print(time.ctime()) #当前系统时间 print(time.ctime(time.time()-86400)) #一天前,将时间转换为字符串 print(time.gmtime()) #时间戳转换为strucktime格式,返回0时区时间,可加时间戳参数 #print(time.gmtime(1473042698.6790164)) print(time.localtime()) #时间戳转换为strucktime格式,返回当前时区时间,可加时间戳参数 x=time.localtime() print(x.tm_year,x.tm_mon,x.tm_mday) print(time.mktime(time.localtime())) #与localtime相反,把stucktime转换为时间戳 print("-----") time.sleep(2) #停顿2秒 print("-----") tm1=time.strftime("%Y-%m-%d %H:%M:%S",time.localtime()) print(tm1) #将 strucktime格式化输出字符串 tm2=time.strptime("2016-09-05 11:12","%Y-%m-%d %H:%M") print(tm2) #将格式化字符串转换为stucktime格式
datetime #常用取时间
import time import datetime print(datetime.date.today()) #当前日期 print(datetime.datetime.now()) #当前时间 print(datetime.datetime.now().replace(2014,9,12)) #替换时间 print(datetime.datetime.now().timetuple()) #返回strucktime格式 print(datetime.datetime.now()+datetime.timedelta(days=10)) #十天后 print(datetime.datetime.now()+datetime.timedelta(days=-10)) #十天前 #timedelta(days=, seconds=, microseconds=,milliseconds=, minutes=, hours=, weeks=)
格式化输出占位符 %Y Year with century as a decimal number. %m Month as a decimal number [01,12]. %d Day of the month as a decimal number [01,31]. %H Hour (24-hour clock) as a decimal number [00,23]. %M Minute as a decimal number [00,59]. %S Second as a decimal number [00,61]. %z Time zone offset from UTC. %a Locale's abbreviated weekday name. %A Locale's full weekday name. %b Locale's abbreviated month name. %B Locale's full month name. %c Locale's appropriate date and time representation. %I Hour (12-hour clock) as a decimal number [01,12]. %p Locale's equivalent of either AM or PM.
random
#产生六位随机验证码 import random l=[] for i in range(6): r=random.randrange(1,3) #50%几率 if r == 1: num=random.randrange(0,10) c=str(num) #数字转字符串 l.append(c) else: temp=random.randrange(65,91) #产生65到90的随机数,65<=temp<91 c=chr(temp) #ascii数字转字母 l.append(c) result="".join(l) #列表各元素合并 print(result)
logging模块
logging的日志可以分为5个级别。
Level | When it’s used |
---|---|
DEBUG |
Detailed information, typically of interest only when diagnosing problems. |
INFO |
Confirmation that things are working as expected. |
WARNING |
An indication that something unexpected happened, or indicative of some problem in the near future (e.g. ‘disk space low’). The software is still working as expected. |
ERROR |
Due to a more serious problem, the software has not been able to perform some function. |
CRITICAL |
A serious error, indicating that the program itself may be unable to continue running. |
import logging logging.basicConfig(filename='test.log',level=logging.INFO, format='%(asctime)s %(message)s',datefmt='%m/%d/%Y %I:%M:%S %p') #打印到test.log文件里,日志级别为INFO,默认WARNING,format格式 logging.debug("DEBUG") logging.info("INFO") logging.warning("WARNING") logging.error("ERROR") logging.critical("CRITICAL")
日志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 |
用户输出的消息 |
logging模块的类
logger提供了应用程序可以直接使用的接口;
handler将(logger创建的)日志记录发送到合适的目的输出;
filter提供了细度设备来决定输出哪条日志记录;
formatter决定日志记录的最终输出格式。
logger
每个程序在输出信息之前都要获得一个Logger,Logger通常对应了程序的模块名,
比如图形界面模块可以这样获得它的Logger:LOG=logging.getLogger("chat.gui")
而核心模块可以这样:LOG=logging.getLogger("chat.kernel")
Logger.setLevel(ERROR):指定最低的日志级别,低于ERROR的级别将被忽略。
Logger.addHandler(hdlr)、Logger.removeHandler(hdlr):增加或删除指定的handler
Logger.debug()、Logger.info()、Logger.warning()、Logger.error()、Logger.critical():可以设置的日志级别
handler
handler对象负责发送相关的信息到指定目的地。
可以通过addHandler()方法添加多个多handler,
Handler.setLevel(lel):指定被处理的信息级别,
Handler.setFormatter():给这个handler选择一个格式1) logging.StreamHandler
使用这个Handler可以向类似与sys.stdout或者sys.stderr的任何文件对象(file object)输出信息。
它的构造函数是:StreamHandler([strm])
其中strm参数是一个文件对象。默认是sys.stderr2) logging.FileHandler
和StreamHandler类似,用于向一个文件输出日志信息。不过FileHandler会帮你打开这个文件。
它的构造函数是:FileHandler(filename[,mode])
filename是文件名,必须指定一个文件名。
mode是文件的打开方式。参见Python内置函数open()的用法。默认是’a',即添加到文件末尾。3) logging.handlers.RotatingFileHandler
这个Handler类似于上面的FileHandler,但是它可以管理文件大小。
当文件达到一定大小之后,它会自动将当前日志文件改名,然后创建一个新的同名日志文件继续输出。
比如日志文件是chat.log。当chat.log达到指定的大小之后,RotatingFileHandler自动把文件改名为chat.log.1。如果chat.log.1已经存在,会先把chat.log.1重命名为chat.log.2最后重新创建 chat.log,继续输出日志信息。
它的构造函数是:RotatingFileHandler( filename[, mode[, maxBytes[, backupCount]]])
其中filename和mode两个参数和FileHandler一样。
maxBytes用于指定日志文件的最大文件大小。如果maxBytes为0,意味着日志文件可以无限大,这时上面描述的重命名过程就不会发生。
backupCount用于指定保留的备份文件的个数。比如,如果指定为2,当上面描述的重命名过程发生时,原有的chat.log.2并不会被更名,而是被删除。4) logging.handlers.TimedRotatingFileHandler
这个Handler和RotatingFileHandler类似,间隔一定时间就自动创建新的日志文件。重命名的过程与RotatingFileHandler类似,新的文件附加当前时间。
它的构造函数是:TimedRotatingFileHandler( filename [,when [,interval [,backupCount]]])
filename与backupCount参数和RotatingFileHandler具有相同的意义。
interval是时间间隔。
when参数是一个字符串。表示时间间隔的单位,不区分大小写。它有以下取值:
S 秒
M 分
H 小时
D 天
W 每星期(interval==0时代表星期一)
midnight 每天凌晨
import logging from logging import handlers # 创建logger logger = logging.getLogger('TEST-LOG') logger.setLevel(logging.DEBUG) # 创建StreamHandler,用于控制台输出 ch = logging.StreamHandler() ch.setLevel(logging.DEBUG) # 创建FileHandler,用于文件输出 fh = logging.FileHandler("access.log") fh.setLevel(logging.WARNING) # 创建TimedRotatingFileHandler,文件输出,按时间自动截取 th = handlers.TimedRotatingFileHandler(filename="log_file",when="S",interval=5,backupCount=3) # 创建formatter formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s') # 把formatter格式加给handler ch.setFormatter(formatter) fh.setFormatter(formatter) th.setFormatter(formatter) # 把handler加给logger logger.addHandler(ch) logger.addHandler(fh) logger.addHandler(th) # 打日志 logger.debug('debug message') logger.info('info message') logger.warn('warn message') logger.error('error message') logger.critical('critical message')