模块知识储备:
1、定义
用来从逻辑上组织python代码(变量、函数、类、逻辑 实现一个功能)。本质上就是 .py结尾的python文件
2、导入方法
Import module_test #导入一个模块
Import module1_test,module2._test #导入两个模块
From module_test import * #表示如果module_test中有几个方法,全部导入 不建议使用
#不建议使用的原因:因为如果在main函数中,如果有一个同方法名的函数调用时,就只执行当前文件
区别:From module_test import * 相当于拷贝了一份都当前文件,直接调用不用带前缀,而Import module_test只是简单导入,需要通过前缀module_test.logger() 才可以调用
From module_test import logger 调用了这个函数,如果在main中也有一个logger函数,两个都要使用的话,通过给module_test中的logger另起别名调用如下:
From module_test import logger as logger_module 这样要调用module中的logger函数时,直接调用别名: logger_module 就是执行调入函数中的logger函数
From . import test1 # 从当前目录下导入test1文件
From module_test import A,B,C导入多个方法
3、import的本质
执行 import module_test就是将module_test解释了一遍,然后将其中的所有的代码都付给了module_test这个变量(module_test =all code)。
这时调用时,就通过变量名.变量,Module_test.logger()、module_test.name就可以调用,故而from module_test import logger 就是通过解释module_test中的logger ,将其中的logger(函数)方法代码全部赋给变量logger此时就相当将logger代码有付给了logger代码,故而就不需要在通过前缀调用,直接调用就可以
导入模块的本质就是把python文件解释(执行)一遍
导入包的本质:就是执行该包下面的__init__.py文件
如果想导入包package_test 就运行下面的__init__.py
如果在__init__.py中写入:print(“from package package_test ”)
和package_test 不在同一个包下面,并且在调用该包的上面一级,只有单独一个.py文件中写入:Import package_test
直接执行 结果为:from package package_test
如果要调用package_test包下面的.py文件,只需要在__init__.py直接调用包下的.py文件
图片解释
"""代码解释三个文件夹:bin {__init__.py atm.py (atm 程序是整个Atm程序的执行文件)} conf { __init__.py setting.py }core(核心代码){ __init__.py main.py(程序的入口) } logs(日志){ 存放日志 }在atm.py 文件中写代码 如果要调用 setting.py 和main.py 两个文件 就必须先找到当前(atm.py)文件的路径,然后通过模块os来一步步向上走,找到要调用文件的上一个路径,atm 然后,再通过from conf import setting 和 from core import main 来调用函数package包下的setting和main模块文件 将你正在编写的.py文件通过os的方式退到要调用的模块的上一级"""
路径知识
1 import os 2 #print(__file__)#相对路径 3 #print(os.path.abspath( __file__))#绝对路径 4 #print(os.path.dirname(os.path.abspath(__file__)))# 往上返回一级 到 bin 返回目录名,不要文件名( 指的是专拣目录结构规范.py文件) 5 print(os.path.dirname( os.path.dirname( os.path.abspath( __file__ ) ) ) )#再往上返回一级到Atm 6 import sys #用于添加环境变量 文件会在这个由环境变量生成的list中去找 7 BASE_DIR =os.path.dirname( os.path.dirname( os.path.abspath( __file__ ) ) ) #此时将返回到Atm的路径赋给变量BASE_DIR 8 sys.path.append(BASE_DIR) #再将找到的这个路径 追加到 sys.path路径模块中去 但是会追加到list的最后一位 9 #万一在sys.path的list中有一个这样的文件,就会执行这个文件,所以可以通过sys.path.insert()查到前面10 #import conf,core #标红是因为pycharm启动时,不知道这个conf,core11 from conf import setting12 from core import main #表示从一个package包下找到.py文件的模块13 main.login()14 #调用的模块在package包外面,直接用 import module_test调用,如果在包里面就必须要通过15 from core import main 来调用 如上:16 import sys,os17 #os 用来调用路径 18 print(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))19 res =os.path.dirname(os.path.dirname(os.path.abspath(__file__)))20 21 sys.path.append(res)22 from xixi import module_test23 module_test.logger()
4、导入优化
如果要调用一个包下的test方法,但要在模块中多次调用,这样每次都要去找module_test.Test这个方法,所以花费时间
解决方法:通过将上面的 import module_test 换成 form module_test import test这样就直接省略了每次都去找module_test.Test的方法,节约时间
5、模块的分类
- 标准库、内置模块
- 开源模块
- 自定义模块
标准库
1、time 和 datetime
在python中,通常有这几种方法来表示时间:1.)时间戳 2.)格式化的时间字符串 3.)元组(struct_time)共九个元素,由于python的time模块实现主要调用C库,所以各个平台可能不同
UTC(coordinated Univerval Time,世界协调时)也成格林威治天文时间,世界标准时间,在中国为UTC+8
DST(Daylight Saving Time)即夏令时
时间戳(timestamp)的方法:通常来说,时间戳表示1970年1月1日00:00:00开始按秒计算的偏移量,我们运行 “ type(time.time() ) ”返回的是float类型,返回时间戳方式的函数主要有time()、clock()等
元组 (struct_time)方式:struct_time()元组共有9个元素,返回struct_time的函数有gmtime()、localtime()、strptime()
时区:将一个地球球体,分成360度,每15度为一个时区,刚好24个时区,以英国刚好在0度,然后中国刚好在东边第8个时区,所以时间要加8,比UTC早了8个小时
import time
help(time)查询时间帮助
时间戳:time.time() 以秒为单位 并且是从1970开始记时
Time.gmtime()讲一个时间戳转换成元祖形式的时间
——如果不加参数就显示现在UTC(标准)的时间,比中国时间迟了8个小时
——如果加上参数,显示的就是所传入时间戳的 元祖表示时间
Time.localtime()
——如果不传,当地的时间(UTC+8时区)
——如果传入,就会显示所传入时间戳转换成元祖的时间
如果要取出元祖表示的时间
Time.mktime()
——讲一个元组形式的变量转换成时间戳形式 因此 一般就是将一个元祖形式的时间赋给一个变量,然后再传值
1 import time 2 x =time.localtime()#表示将本地的时间赋给 x 变量 3 print(x) 4 print(time.strftime("%Y-%m-%d %H:%M:%S",x)) 5 print(time.strptime('2018-02-02 12:26:50',"%Y-%m-%d %H:%M:%S")) 6 print(x.tm_year) 7 #print(learn module.mktime(x)) #将一个元祖形式的时间转换成时间戳形式的时间 8 #print(help(x))#表示 x所有的方法 9 #print(x.tm_year)#通过上面 print(help(x)) 就可以知道要去除年就通过x.tm_year10 #print(help(learn module.strftime))
struct_time、timestamp、 format string 之间的关系
Datetime
Datetime.date #包含的是 年-月-日
Datetime.time #包含的是时-分-秒
Datetime.datetime #包含的是 年-月-日-时-分-秒
1 Import datetime2 Datetime.datetime.now()#表示现在的时间3 函数datetime.timedelta(3)不能单独使用,必须与Datetime.datetime.now()连用如下:4 Datetime.datetime.now()+datetime.timedelta(3)#现在时间的三天后5 Datetime.datetime.now()+datetime.timedelta(-3)#现在时间的三天前 默认单位为天6 Datetime.datetime.now()+datetime.timedelta(hours =3)#现在时间的三个小时后7 Datetime.datetime.now()+datetime.timedelta(hours =-3)#现在时间的三个小时前8 Datetime.datetime.now()+datetime.timedelta(minute =30)#现在时间的30分钟后9 Datetime.datetime.now()+datetime.timedelta(minute =-30)#现在时间的30分钟前
2、random
1 Random.random()#随机数表示在[0,1)之间的随浮点数2 Random.randint(1,3)#表示[1,3] 1,2,3这三个随机整数3 Random.randrange(1,3)#表示[1,2) 1,2 这两个随机整数 4 Random.choice( )#括号中可为:序列、tuple、list、dictionary 随机在括号中选择5 Random.choice(‘hello,world’)#表示在hello,world中随机选择 其他同理6 Random.sample(‘ ……’ , 数字)#第一个写序列,同上一样,后面写数字表示随机的在前面写的序列中选择几位
随机验证码程序例子:
1 # import random 2 # s =[1,2,3,4,5,6] 3 # random.shuffle(s) #表示将上面的数据随机洗乱依次 洗牌 4 # print(s) 5 # random.shuffle(s) 6 # print(s) 7 import random 8 checkcode =''#先写一个空字符串来存放生成的验证码值 9 for i in range(4): #如果有四位验证码10 current =random.randrange(0,4) #先随机产生四个数字,来分成两部分11 if current==i:#如果循环的次数和产生的数字相同12 tmp =chr(random.randint(65,90)) #就在大写字母A—Z中随机产生13 # chr()是将ascii表中的数字变成字母14 else:15 tmp =random.randint(0,9)#如果循环的次数和产生的数字不相同,就在数字0-9中产生16 checkcode+=str(tmp) #将生成全部存在checkcode空字符串中17 print(checkcode) #然后输出
在运行过程出现的错误:
#如果所起的模块名字和标准库中模块的名字相同时,会出现以下情况:
例子: 当在通过import random调用random模块时,把文件名写成了random
1、在文件中就无法调用random标准库中的方法,如果调用会报错
2、如果没有调用到random模块下的方法时,顺利运行程序后,会出现两个相同的输出,就是文件中只有一处有print 如上
3、os模块
1 >>> os.stat(r"f:\pycharm\heihei")#获取文件/目录2 >>> os.rename(r"f:\pycharm\shiyan",r"f:pycharm\heihei")#重命名3 >>> os.makedirs(r"d:a\b\c\d")#可生成多层递归目录4 >>> os.removedirs(r"d:a\b\c\d")#若目录为空则删除,且返回到上一级目录,若为空仍删除以此类推5 就是将多个路径拼接在一起如下:6 >>> os.path.join(r'f:',r'\b',r'a.txt') #结果为:'f:\\b\\a.txt'7 Os.path.getatime() #返回path所指向的文件或者目录的最后存取时间8 Os.path.getmtime() # 返回path所指向的文件或者目录的最后修改时间
View Code
4.sys.模块
1 sys.argv #命令行参数list,第一个元素是程序本身路径2 sys.exit(n) #退出程序,正常退出时exit(0)3 sys.version #获取python解释程序的版本信息4 sys.path #返回模块的搜索路径初始化时使用pythonpath环境变量的值5 sys.platform #返回操作系统平台名称6 sys.stdout.write('please:')#返回结果: please:7
5、shutil模块
功能:高级文件、文件夹、压缩包、处理模块
1 Shutil.copy(src,dst) #拷贝文件和权限 2 def copy(src, dst): 3 """Copy data and mode bits ("cp src dst"). 4 The destination may be a directory. """ 5 shutil.copymode(src, dst)# 仅拷贝权限。内容、组、用户均不变 6 def copymode(src, dst): 7 """Copy mode bits from src to dst""" 8 shutil.copystat(src, dst) 9 拷贝状态的信息,包括:mode bits, atime, mtime, flags10 def copystat(src, dst):11 """Copy all stat info (mode bits, atime, mtime, flags) from src to dst"""12 shutil.copy2(src, dst)#拷贝文件和状态信息13 def copy2(src, dst):14 """Copy data and all stat info ("cp -p src dst").15 The destination may be a directory. """16 shutil.copytree(src, dst, symlinks=False, ignore=None)17 #递归的去拷贝文件,旧目录拷贝到新目录 连下面的子目录都一起拷贝18 Shutil.copytree(“test4”,”new_test4”)#其中test4和new_test4都是一个包19 shutil.rmtree(path[, ignore_errors[, onerror]])20 递归的去删除文件21 Shutil.rmtree(“new_test4”)#删除new_test4整个包以及下面的子目录22 shutil.move(src, dst)#递归的去移动文件
shutil.make_archive(base_name, format,...) 创建压缩包并返回文件路径,例如:zip、tar
1 #自己测试 2 shutil.make_archive("压缩测试","zip","F:\pycharm\day5")#第一个为压缩的名称;第二个为压缩的类型;第三个为要压缩文件的路径 3 4 shutil 对压缩包的处理是调用 ZipFile 和 TarFile 两个模块来进行的,详细: 5 6 zipfile 压缩解压 7 import zipfile 8 # 压缩 9 z = zipfile.ZipFile('laxi.zip', 'w')10 z.write('a.log')11 z.write('data.data')12 z.close()13 14 # 解压15 z = zipfile.ZipFile('laxi.zip', 'r')16 z.extractall()17 z.close()18 Eg:19 import zipfile20 #压缩单个压缩.zip21 z =zipfile.ZipFile('单个压缩.zip','w')#压缩包名:单个压缩.zip 操作为:写 默认为:读22 z.write('F:\pycharm\day3\\test.py')#写上路径23 print('-----中间可以干别的事情-------')24 z.write('F:\pycharm\day6\module_test1\path.py')25 z.close()26 #解压单个压缩.zip27 z = zipfile.ZipFile('单个压缩.zip','r')28 z.extractall()29 z.close()30 31 zipfile 压缩解压32 33 import tarfile34 # 压缩35 tar = tarfile.open('your.tar','w')36 tar.add('/Users/wupeiqi/PycharmProjects/bbs2.zip', arcname='bbs2.zip')37 tar.add('/Users/wupeiqi/PycharmProjects/cmdb.zip', arcname='cmdb.zip')38 tar.close()39 # 解压40 tar = tarfile.open('your.tar','r')41 tar.extractall() # 可设置解压地址42 tar.close()
5、json&pickle
json,用于字符串 和 python数据类型间进行转换
pickle,用于python特有的类型 和 python的数据类型间进行转换
Json模块提供了四个功能:dumps、dump、loads、load
pickle模块提供了四个功能:dumps、dump、loads、load
由于在python中,通过json和pickle多次dumps之后如果在load的时候,就会出现错误,因为在通过load要取出某一次值的时候就必须要记住dump了几次,否则就无法顺利取出,为了解决这个问题就引入了shelve模块
6、shelve 模块
1 import shelve,datetime 2 d = shelve.open("shelve_test")#通过shelve方法将文件名为shelve_test的文件打开,方法和file一样 3 info ={ 'age':23,'job':'it'} 4 name =['zhangsan','lisi','wangwu'] 5 """以关键字key的形式 将 字典、列表、数据等 写入文件保存, 6 之后后面会出现数字,就是用来进行序列化,这样就会很快查找""" 7 d['info']=info #持久的dictionary 8 d['name']=name#持久的list 9 d['date']=datetime.datetime.now()#持久的date10 """11 通过d.get(key)就可以将存入的东西取出文件12 """13 print(d.get("info"))14 print(d.get("name"))15 print(d.get("date"))16 d.close()
7、xml处理文件
xml是实现不同语言或程序之间进行数据交换的协议,跟json差不多,但json使用起来更简单,不过,古时候,在json还没诞生的黑暗年代,大家只能选择用xml呀,至今很多传统公司如金融行业的很多系统的接口还主要是xml。
xml的格式如下,就是通过<>节点来区别数据结构的:
1 23 92 42012 5141100 67 8 10 155 112015 1259900 1314 16 2269 172015 1813600 1920 21
xml协议在各个语言里的都 是支持的,在python中可以用以下模块操作xml
1 import xml.etree.ElementTree as ET 2 tree = ET.parse("xml_test.xml") 3 root = tree.getroot() 4 #print(root)#表示 xml_test.xml 的根目录date的内存地址 5 print(root.tag) #root.tag 表示在xml_test.xml 中root的名称 6 7 #遍历xml文档 8 for child in root: #child是root的下一级目录的内存地址 9 # print(child.tag)#root的下一级目录 (即country)10 print(child.tag,child.attrib)#root的下一级目录 country的内存地址11 for i in child: #root的下一级目录的下一级目录12 print(i.tag, i.text)#i.tag是root的下一级目录的下一级目录标题,13 # i.text#root的下一级目录的下一级目录的内容14 15 # 只遍历year 节点16 for node in root.iter('year'):17 print(node.tag, node.text)#遍历year这个节点并且和year的参数
Xml_test修改和删除
1 import xml.etree.ElementTree as ET 2 3 tree = ET.parse("xml_test.xml") 4 root = tree.getroot() 5 6 # 修改 7 for node in root.iter('year'):#通过root.iter()找到year这个目录 8 new_year = int(node.text) + 1 #因为node.text中的year是一个字符串,先转成int类型再加 1 9 node.text = str(new_year) #要将int类型的new_year转化成str(new_year)在存储10 node.set("updated", "yes")"""2012 11 其中等于yes说明已经修改,而后面的updated_by="zss"表示由谁修改12 node.set("updated_by", "zss") #可以再将year后加上任何属性(可以是自己随便定义的)"""13 tree.write("xml_test.xml")#再将上面修改的内容存储到xml_test.xml文档中14 15 # 删除node16 for country in root.findall('country'):#找到所有的country并循环country17 rank = int(country.find('rank').text)#并且找到所有country下的'rank',将其后面的字符串数字转换成int类型的数字并赋值rank变量 并且为一个.text的文件18 if rank > 50:#在判断rank的值是否大于5019 root.remove(country)#如果小于50则移除这个rank所在的country标签以及下面的所有内容20 21 tree.write('output.xml')#在将其写入新建立的一个output.xml文件中
Xml文件的创建
1 import xml.etree.ElementTree as ET#先找到ET的内存对象,然后最后在生成一个文档 2 3 new_xml = ET.Element("namelist") #namelist为根节点 4 z = ET.SubElement(new_xml, "personinfo", attrib={ "enrolled": "yes"})#在根节点new_xml下,创建一个name的子节点,属性为字典中的值 5 age = ET.SubElement(z, "age", attrib={ "checked": "no"})#在name的子节点下在创建一个子节点age,属性为attrib之后的内容 6 name1 = ET.SubElement(z, "name", attrib={ "checked": "no"}) 7 name1.text ="zss" 8 sex = ET.SubElement(z, "sex")#再在name的子节点下创建一个sex的子节点 9 age.text = '33' #年龄为3310 s = ET.SubElement(new_xml, "personinfo2", attrib={ "enrolled": "no"})#其中的括号中的personinfo2为namelist根节点的子节点,前面的personinfo2是一个变量代表了personinfo2这个子节点11 age = ET.SubElement(s, "age")12 age.text = '19'13 name2 = ET.SubElement(s, "name", attrib={ "checked": "no"})14 name2.text="zhangsan"15 et = ET.ElementTree(new_xml) # new_xml为生成文档对象16 et.write("test.xml", encoding="utf-8", xml_declaration=True)#文件名为test.xml 编码格式为utf-8 为一个版本号17 18 ET.dump(new_xml) # 打印生成的格式
要在python中添加一个标签有下列的要求
变量名=ET,ElementTree(父节点,“要添加的标签”,要添加的属性)
变量名.text ="标签包起来要显示的内容"
8、ymal语法 需要下载库
9、Configparser模块
写一个配置文件
1 import configparser 2 #写一个配置文件config 3 config = configparser.ConfigParser()#先把对象调进来然后在赋给变量config 4 5 config["DEFAULT"] = { 'ServerAliveInterval': '45', #第一个节点 6 'Compression': 'yes', 7 'CompressionLevel': '9'} 8 9 config['bitbucket.org'] = {} #第二个节点10 config['bitbucket.org']['User'] = 'hg'11 config['topsecret.server.com'] = {} #第三个节点12 13 topsecret = config['topsecret.server.com'] #点三个节点14 topsecret['Host Port'] = '50022' # mutates the parser15 topsecret['ForwardX11'] = 'no' # same here16 config['DEFAULT']['ForwardX11'] = 'yes'17 with open('example.ini', 'w') as configfile:18 config.write(configfile)
配置文件的读和删
1 '''用于生成和修改常见配置文档,当前模块的名称在 python 3.x 版本中变更为 configparser。2 如果要生成一个以.config为后缀的文档时,先在其中建立一个.py文件,输入完成后在重命名为.config'''3 import configparser4 config=configparser.ConfigParser()5 print(config.sections())# 因为没有读文件,所以输出一个空的list6 print(config.read('example.ini'))7 print(config.sections())#但是打印了两个 因为default是默认的,所以只打印节点 而不打印defalut8 print(config.defaults())#读defaults中的文档内容9 print(config['bitbucket.org']['user'])#读bitbucket.org下user的信息
10、hashlib模块
用于加密相关的操作,3.x里代替了md5模块和sha模块,主要提供 SHA1, SHA224, SHA256, SHA384, SHA512 ,MD5 算法 md5值是不能反解的
1 import hashlib 2 m =hashlib.md5()#要加密对象存放的地方 3 m.update(b"Hello")#b'hello' bytes 类型 4 print(m.hexdigest())#表示十六进制来加密 bytes类型的 hello 5 # m =hashlib.md5() 6 m.update(b"It's me" ) 7 print(m.hexdigest()) #表示用十六进制来加密helloit's me这两句 8 """验证是否相同 将两个bytes类型的东西全部放在一起打印出来 9 如果结果相同的话就表示是将上面两个连起来加密10 但是如果是通过两个m.update(b'')来起来的话,共用一个11 m=hashlib.md5() 结果相同,但是两个分别用了一次 m=hashlib.md5()12 那么结果就不相同,因为相同时通过共用一个 m=hashlib.md5(),使得13 m是完全相同的,之后的就是m的更新"""14 m2 = hashlib.md5()15 m2.update(b"HelloIt's me")16 print(m2.hexdigest())17 18 # 如果有中文就必须要通过下列方式进行加密19 m2 = hashlib.md5()20 m2.update("天王盖地虎,宝塔镇河妖".encode(encoding="utf-8"))#可以运行 顺利加密21 print(m2.hexdigest())
python 还有一个 hmac 模块,它内部对我们创建 key 和 内容 再进行处理然后再加密 散列消息鉴别码,简称HMAC,是一种基于消息鉴别码MAC(Message Authentication Code)的鉴别机制。使用HMAC时,消息通讯的双方,通过验证消息中加入的鉴别密钥K来鉴别消息的真伪;
一般用于网络通信中消息加密,前提是双方先要约定好key,就像接头暗号一样,然后消息发送把用key把消息加密,接收方用key + 消息明文再加密,拿加密后的值 跟 发送者的相对比是否相等,这样就能验证消息的真实性,及发送者的合法性了。
更多关于md5,sha1,sha256等介绍的文章看这里 https://www.tbs-certificates.co.uk/FAQ/en/sha256.html
1 import hmac2 s2 =hmac.new(b"124",b"sdfsdf")3 s2 =hmac.new(b"124","我放假死灵法师".encode(encoding="utf-8"))#可以运行 并顺利加密4 s2 =hmac.new(b"jkhj","我放假死灵法师".encode(encoding="utf-8"))#可以运行并顺利加密5 s2 =hmac.new("网址之王".encode(encoding="utf-8"))#可以运行 并且顺利加密6 s2 =hmac.new("网址之王","我放假死灵法师".encode(encoding="utf-8")) #不可以运行 出错7 print(s2.hexdigest())
11、re模块(正则表达式) 用于匹配字符串
'.' 默认匹配除\n之外的任意一个字符,若指定flag DOTALL,则匹配任意字符,包括换行'^' 匹配字符开头,若指定flags MULTILINE,这种也可以匹配上(r"^a","\nabc\neee",flags=re.MULTILINE)'$' 匹配字符结尾,或e.search("foo$","bfoo\nsdfsf",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") 是匹配不到的'\Z' 匹配字符结尾,同$'\d' 匹配数字0-9'\D' 匹配非数字'\w' 匹配[A-Za-z0-9]'\W' 匹配非[A-Za-z0-9]'\s' 匹配空白字符、\t、\n、\r , re.search ("\s+","ab\tc1\n3").group() 结果 '\t''(?P...)' 分组匹配 re.search("(?P [0-9]{4})(?P [0-9]{2})(?P [0-9]{4})","371481199306143242").groupdict("city") 结果: { 'province': '3714', 'city': '81', 'birthday': '1993'}
最常用的匹配语法re.match 从头开始匹配re.search 匹配包含re.findall 把所有匹配到的字符放到以列表中的元素返回re.splitall 以匹配到的字符当做列表分隔符re.sub 匹配字符并替换
总结:
+ 表示 会按照它前面字符的样式来打印多个. 表示 打印除\n(换行)外的所有字符.+ 组合才会全部包括后面的数字 打印之后的所有字符[a-z] 表示 打印一个小写字母;[A-Z]表示:打印一个大写字母 [a-z] + [A-Z] 可以组合起来用("z[a-z]+[A-Z]+","jiang123zhongzHenzhongzhen1232424124zhongzhen")Eg:一、z[a-z]+[A-Z]+.+ 就是将上面从z开始打印完 结果:zhongzHenzhongzhen1232424124zhongzhen二、"z[a-zA-Z]+\d+" 就是将上面从z开始打印到结果:zhongzHenzhongzhen1232424124
重点知识
1 res=re.search("aaaaz?","azhangaaaa")# 表示 ?前面的那个 z有和没有都可以 但是z?前面的那些a必须都要匹配到,如果匹配不到就 报错,可以匹配到就输出 2 res =re.findall("[0-9]{1,3}","z1h23a456n7g8") re.findall() 没有group方法 3 print(res) #结果为:['1', '23', '456', '7', '8'] 4 res =re.findall("[0-9]{1,2}","z1h23a456n7g8") 5 print(res) #结果为:['1', '23', '45', '6', '7', '8'] 6 res =re.findall("[0-9]{3}","z1h23a456n7g8") 7 print(res) #结果为:['456'] 8 9 '''重点'''10 res=re.search("(?P[0-9]{2})(?P [0-9]{2})(?P [0-9]{2})(?P [0-9]{4})","371481199306143242")11 print(res.groupdict()) #其中的 ?P 表示语法 [范围]{几位} 结果为:{'province': '37', 'shi': '14', 'city': '81', 'birthday': '1993'} 并且还可以再加几组字典12 print(res.groupdict()['city']) # 相当于取出字典中的key=’city’结果为:81
re.sub()知识使用
re.sub(pattern,repl,string,count=0,flags =0) 替换
pattern:表示要匹配的值repl:要替换成什么 这里是写定值,不能比正则表达式string:在“”中进行匹配count:表示替换几次eg:res =re.sub("[0-9]","|","ab2h4h35g42g",count=2)print(res) #结果为: ab|h|h35g42g扩展:
re.I(re.IGNORECASE): 忽略大小写(括号内是完整写法,下同)
M(MULTILINE): 多行模式,改变'^'和'$'的行为(参见上图)
S(DOTALL): 点任意匹配模式,改变'.'的行为
re模块用法案例:
1 Eg:res =re.search("[a-z]+","zhangSHuai",flags =re.I)# flag =re.I 忽略大小写 结果为:zhangSHuai 2 print(res.group()) 3 4 """re(正则表达式)就是用于动态匹配的 如果是一个固定值,就不需要通过re来进行 直接通过 wang in wangmazi:就可以进行匹配 """ 5 6 7 import re 8 """re.match 的用法:就是默认从头开始的, 9 ^ 表示要匹配字符开头 故而 ^ 在match中没有用10 第一个""写的是要匹配的内容,后面的""写的是匹配度的范围11 res =re.match("^wang","wang mazi")12 print(res) #如果有返回结果 就表示匹配到了 如果没有匹配到就返回 None13 print(res.group())#通过res.group()来查看匹配到什么"""14 15 """ \d+的用法16 \ 表示后面是用于正则的语法,\d表示一个数字 结果为:wang2,17 \d+表示一个或多个数字结果为:wang23418 res =re.match("wang\d+","wang234 mazi ")19 print(res.group())20 """21 22 """ . 的用法23 res =re.match(".","@wang234 mazi ")# . 默认匹配除\n之外的任意一个字符 在此处打印 @24 # res =re.match(".+","wang234 mazi ")# + 表示打印后面的多个 故而: .+ 打印全部25 # res =re.match(".\d","w1ang234 mazi ")#如果第一位是 w 第二个为数字就可以执行,否则就会报错26 # res =re.match("^w","wang234 mazi ")27 print(res.group())"""28 29 30 """re.serach的用法 表示从整个内容中搜查 这是会用到 ^ 符号"""31 #res = re.search("z.+n","jiang123zhongzhen123a")#从z开始 通过.+就z之后一直到32 #后面的 n 如果前面+之后没有n就会包括12333 34 #res =re.search("z[a-z]+.+2","jiang123zhong zhen123a")35 """36 [a-z]输出一个在a到z之间的一个字符, + 表示多个字符,第一个 + 从o取到g37 然后 . 表示一个除\n(换行)外的任意一个字符取出空格, 第二个加号表示38 从 z 一直往后取到加号后面的截止字符 结果为:zhong zhen1239 res =re.search("z[a-z]+[A-Z]+.+","jiang123zhongzHenzhongzhen1232424124zhongzhen")#输出结果为:zhongZhenzhongzhen40 #res =re.search("z[a-zA-Z]+\d+","jiang123zhongzHenzhongzhen1232424124zhongzhen")41 res =re.search("#.+#","123#hello#")#结果为:#hello#42 print(res.group())"""43 # res=re.search("aaaaa?","azhangaaaa")#表示?前面的那个a有和没有都可以 但是a?前面的那些a必须要匹配到44 # print(res.group())45 46 47 """re.findall() 匹配不相连的多个数字 并且没有group()方法48 #res =re.findall("[0-9]{1,2}","z1h23a456n7g8")#结果为:['1', '23', '45', '6', '7', '8']49 #res =re.findall("[0-9]{1,3 }","z1h23a456n7g8")#结果为:['1', '23', '456', '7', '8']50 res =re.findall("[0-9]{3}","z1h23a456n7g8")#结果为:['456']51 52 print(res)"""53 54 res=re.search("abc|ABC","ABCBabcdB")#先匹配小写或者再匹配大写 返回结果:ABC55 res=re.search("abc{2}","abccadf") #匹配abc并且c匹配两次 即:必须要有abcc才可以才返回,否则报错56 res =re.search("(abc){2}","abcabcadf")#同上 将abc当做一个小组,同时匹配两次 即:abcabc 否则报错57 res =re.search("(abc){2}\|","abcabcadf")#同理 \ 表示转义符,代表不要将 |当做或l来处理 有abcabc| 时才输出,否则报错58 res =re.search("(abc){2}(\|\|=){2}","sdabcabc||=||=adf")# 每一个 \| 都要用输出结果为:abcabc||=||=59 res =re.search("\A[0-9]+[a-z]+\Z","123sdf")#\A等同于 ^ ,表示从第一个元素开始,从第一个为数字,然后经过几个数,然后经过几个字母\Z表示以 字母结束60 res =re.search("\D+","123&%*- A@ \\n") #\D匹配不是数字的任意一个字符 特殊字符可以 换行也可以 结果为:&%*- A@ \n61 res =re.search("\w+","123&%*- A@ \\n")# 小写的 \w只匹配数字和字母 结果为:12362 res =re.search("\W+","123&%*- A@ \\n")#只匹配特殊字符 结果为:&%*-63 #res =re.search("\s+","\r\t\n123&%*- A@ ")64 res=re.search("(?P[0-9]{2})(?P [0-9]{2})(?P [0-9]{2})(?P [0-9]{4})","371481199306143242")65 #其中的 ?P 表示语法 [范围]{几位} 结果为:{'province': '37', 'shi': '14', 'city': '81', 'birthday': '1993'}66 print(res.groupdict()['city'])67 res =re.split("[0-9]+","ab2h4h35g42g") # 因为[0-9]只是一个字符,故而表示将后面的内容# 以数字分隔开,然后是单个数字的去掉,68 多个数字的就以空字符显示出来并与分隔开的字母形成列表 结果为:['ab', 'h', 'h', '', 'g', '', 'g']69 res =re.sub("[0-9]+","|","ab2h4h35g42g",count=2)70 print(res)71 res =re.search("[a-z]+","zhangSHuai",flags =re.I)# flag =re.I 忽略大小写 结果为:zhangSHuai72 print(res.group())
参考文献
http://www.cnblogs.com/wupeiqi/articles/4963027.html