python day7
一、configparser 模块
用于处理特定格式的文件,其本质上是利用open来操作文件。
示例文件
[section1] # 节点
k1 = v1 # 值
k2:v2 # 值
[section2] # 节点
k1 = v1 # 值
测试,获得aa文件的特定格式信息
文件 aa
[section1]
k1 = v1
k2 = v2
[section2]
k1 = v1
1、获取所有节点
import configparser
config = configparser.ConfigParser()
config.read('aa', encoding='utf-8') #读aa文件
ret = config.sections() #获取并形成格式
print(ret)
结果
['section1', 'section2']
2、获取指定节点下所有的键值对
import configparser
config = configparser.ConfigParser()
config.read('aa', encoding='utf-8')
ret = config.items('section1') #使用items获取section1节点键值对
print(ret)
结果
[('k2', 'v2'), ('k10', '123')]
3、获取指定节点下所有的建
import configparser
config = configparser.ConfigParser()
config.read('aa', encoding='utf-8')
ret = config.options('section1') #使用options获取section1的key
print(ret)
结果
['k1', 'k2']
4、获取指定节点下指定key的值
import configparser
config = configparser.ConfigParser()
config.read('aa', encoding='utf-8')
v = config.get('section1', 'k1') #使用get获取section1键k1的值
# v = config.getint('section1', 'k1')
# v = config.getfloat('section1', 'k1')
# v = config.getboolean('section1', 'k1')
print(v)
结果
v1
5、检查、删除、添加节点
import configparser
config = configparser.ConfigParser()
config.read('aa', encoding='utf-8')
# 检查
has_sec = config.has_section('section1')
print(has_sec)
# 添加节点
config.add_section("SEC_1")
config.write(open('aa', 'w'))
# 删除节点
config.remove_section("SEC_1")
config.write(open('aa', 'w'))
结果:
True
6、检查、删除、设置指定组内的键值对
import configparser
config = configparser.ConfigParser() #必须有
config.read('aa', encoding='utf-8') #必须有
# 检查
has_opt = config.has_option('section1', 'k1') #检查节点对应的key是否存在,存在True,不存在False
print(has_opt)
# 删除
config.read('aa', encoding='utf-8')
config.remove_option('section1','k1') #删除section1节的k1键值对
config.write(open('aa','w'))
# 设置
config.set('section1', 'k10', "123") #有则修改,无则添加
config.write(open('aa', 'w'))
二、XML
浏览器返回的字符串
a. HTML
b. json
c. XML
页面上做展示(字符串类型的一个xml格式数据)
配置文件(文件,内部数据xml格式)
XML是实现不同语言或程序之间进行数据交换的协议,XML文件格式如下:
xo.xml
<data> #<data>为根 (名自定义)
<country name="Liechtenstein"> #<country为节点,后面跟属性>
<rank updated="yes">2</rank>
<year>2023</year>
<gdppc>141100</gdppc>
<neighbor direction="E" name="Austria" />
<neighbor direction="W" name="Switzerland" />
</country>
<country name="Singapore">
<rank updated="yes">5</rank>
<year>2026</year>
<gdppc>59900</gdppc>
<neighbor direction="N" name="Malaysia" />
</country>
<country name="Panama">
<rank updated="yes">69</rank>
<year>2026</year>
<gdppc>13600</gdppc>
<neighbor direction="W" name="Costa Rica" />
<neighbor direction="E" name="Colombia" />
</country>
</data>
1.解析xml
使用ElementTree
xo.xml
<data1 title="CTO" age="19">
<country name="Liechtenstein" age="18">
<rank updated="yes">2</rank>
<year>2023</year>
<gdppc>141100</gdppc>
<neighbor direction="E" name="Austria" />
<neighbor direction="W" name="Switzerland" />
</country>
<country name="Singapore">
<rank updated="yes">5</rank>
<year>2026</year>
<gdppc>59900</gdppc>
<neighbor direction="N" name="Malaysia" />
</country>
<country name="Panama">
<rank updated="yes">69</rank>
<year>2026</year>
<gdppc>13600</gdppc>
<neighbor direction="W" name="Costa Rica" />
<neighbor direction="E" name="Colombia" />
</country>
</data1>
-----test.py脚本
利用ElementTree.parse将文件直接解析成xml对象
from xml.etree import ElementTree as ET
tree = ET.parse('xo.xml')
root = tree.getroot() #获取xml根
print(root.tag,'\n\n')
for child in root:
print(child.tag,child.attrib) #获取节点字符,属性
for gradechild in child:
print(gradechild.tag, gradechild.text) #获取节点名,节点内容
结果:
<Element 'data1' at 0x00000000006B71D8>
country {'age': '18', 'name': 'Liechtenstein'}
rank 2
year 2023
gdppc 141100
neighbor None
neighbor None
country {'name': 'Singapore'}
rank 5
year 2026
gdppc 59900
neighbor None
country {'name': 'Panama'}
rank 69
year 2026
gdppc 13600
neighbor None
neighbor None
2.操作XML
两种操作xml方式
解析字符串方式打开,删除,保存
将字符串解析成xml特殊对象 ET.XML(str_xml),用open
解析文件方式打开,删除,保存
直接解析xml文件 ET.parse("xo.xml"),不用open(程序内容实现)
示例xml
<data1 title="CTO" age="19">
<country name="Liechtenstein" age="18">
<rank updated="yes">2</rank> #内容为2
<year>2023</year>
<gdppc>141100</gdppc>
<neighbor direction="E" name="Austria" />
<neighbor direction="W" name="Switzerland" />
</country>
<country name="Singapore">
<rank updated="yes">5</rank> #内容为5
<year>2026</year>
<gdppc>59900</gdppc>
<neighbor direction="N" name="Malaysia" />
</country>
<country name="Panama">
<rank updated="yes">69</rank> #内容为69
<year>2026</year>
<gdppc>13600</gdppc>
<neighbor direction="W" name="Costa Rica" />
<neighbor direction="E" name="Colombia" />
</country>
ET.XML方法---用open
ET.parse方法---不用open
由于 每个节点 都具有以上的方法,并且在上一步骤中解析时均得到了root(xml文件的根节点),so 可以利用以上方法进行操作xml文件。
a. 遍历XML文档的所有内容
from xml.etree import ElementTree as ET
#解析方式一 ET.XML方法---用open
"""
str_xml = open('xo.xml', 'r').read() # 打开文件,读取XML内容
root = ET.XML(str_xml) # 将字符串解析成xml特殊对象,root代指xml文件的根节点
"""
#解析方式二 ET.parse方法---不用open
tree = ET.parse("xo.xml") # 直接解析xml文件
root = tree.getroot() # 获取xml文件的根节点
#操作
print(root.tag) # 顶层标签
for child in root: # 遍历XML文档的第二层
print(child.tag, child.attrib) # 第二层节点的标签名称和标签属性
for i in child: # 遍历XML文档的第三层
print(i.tag,i.text) # 第二层节点的标签名称和内容
结果
data1
country {'name': 'Liechtenstein', 'age': '18'}
rank 2
year 2023
gdppc 141100
neighbor None
neighbor None
country {'name': 'Singapore'}
rank 5
year 2026
gdppc 59900
neighbor None
country {'name': 'Panama'}
rank 69
year 2026
gdppc 13600
neighbor None
neighbor None
b、遍历XML中指定的节点
from xml.etree import ElementTree as ET
#解析方式一 ET.XML方法---用open
"""
str_xml = open('xo.xml', 'r').read() # 打开文件,读取XML内容
root = ET.XML(str_xml) # 将字符串解析成xml特殊对象,root代指xml文件的根节点
"""
#解析方式二 ET.parse方法---不用open
tree = ET.parse("xo.xml") # 直接解析xml文件
root = tree.getroot() # 获取xml文件的根节点
#操作
print(root.tag) # 顶层标签
for node in root.iter('year'): # 遍历XML中所有的year节点
print(node.tag, node.text) # 节点的标签名称和内容
结果
data1
year 2023
year 2026
year 2026
c、修改节点内容
由于修改的节点时,均是在内存中进行,其不会影响文件中的内容。所以,如果想要修改,则需要重新将内存中的内容写到文件。
(1) ET.XML方法--用open
from xml.etree import ElementTree as ET
#解析方式一 ET.XML方法--用open
str_xml = open('xo.xml', 'r').read() # 打开文件,读取XML内容
root = ET.XML(str_xml) # 将字符串解析成xml特殊对象,root代指xml文件的根节点
#操作
print(root.tag) # 顶层标签
for node in root.iter('year'): # 循环所有的year节点
new_year = int(node.text) + 1 # 将year节点中的内容自增一
node.text = str(new_year)
node.set('name', 'alex') # 设置属性,添加name属性信息
node.set('age', '18')
del node.attrib['name'] # 删除属性,与year相匹配的name,即上面的name为alex的属性
#保存文件
tree = ET.ElementTree(root)
tree.write("newnew.xml", encoding='utf-8')
(2) ET.parse方法---不用open-
from xml.etree import ElementTree as ET
#解析方式二
tree = ET.parse("xo.xml") # 直接解析xml文件
root = tree.getroot() # 获取xml文件的根节点
#操作
print(root.tag) # 顶层标签
for node in root.iter('year'): # 循环所有的year节点
new_year = int(node.text) + 1 # 将year节点中的内容自增一
node.text = str(new_year)
node.set('name', 'alex') # 设置属性,添加name属性信息
node.set('age', '18')
del node.attrib['name'] # 删除属性,与year相匹配的name,即上面的name为alex的属性
#保存文件
tree.write("newnew.xml", encoding='utf-8')
结果
<data1 age="19" title="CTO">
<country age="18" name="Liechtenstein">
<rank updated="yes">2</rank>
<year age="18">2024</year>
<gdppc>141100</gdppc>
<neighbor direction="E" name="Austria" />
<neighbor direction="W" name="Switzerland" />
</country>
<country name="Singapore">
<rank updated="yes">5</rank>
<year age="18">2027</year>
<gdppc>59900</gdppc>
<neighbor direction="N" name="Malaysia" />
</country>
<country name="Panama">
<rank updated="yes">69</rank>
<year age="18">2027</year>
<gdppc>13600</gdppc>
<neighbor direction="W" name="Costa Rica" />
<neighbor direction="E" name="Colombia" />
</country>
d、删除节点
功能:实现删除rank节点内容大于50的内容,并将修改后内容写入新文件
(1) ET.XML方法--用open---解析字符串方式打开,删除,保存
#!/usr/bin/env python
#-*- coding:utf-8 -*-
# Author:Minghu Wang
from xml.etree import ElementTree as ET
#解析字符串方式打开
str_xml = open('xo.xml', 'r').read() # 打开文件,读取XML内容
root = ET.XML(str_xml) # 将字符串解析成xml特殊对象,root代指xml文件的根节点
#操作
print(root.tag) # 顶层标签
for country in root.findall('country'): # 遍历data下的所有country节点
rank = int(country.find('rank').text) # 获取每一个country节点下rank节点的内容
if rank > 50: # 内容数字大于50的删除
root.remove(country) # 删除指定country节点
#保存文件
tree = ET.ElementTree(root)
tree.write("newnew.xml", encoding='utf-8') # 写入到新文件
(2) ET.parse方法---不用open--解析文件方式打开,删除,保存
from xml.etree import ElementTree as ET
#解析文件方式
tree = ET.parse("xo.xml") # 直接解析xml文件
root = tree.getroot() # 获取xml文件的根节点
#操作
print(root.tag) # 顶层标签
for country in root.findall('country'): # 遍历data下的所有country节点
rank = int(country.find('rank').text) # 获取每一个country节点下rank节点的内容
if rank > 50:
root.remove(country) # 删除指定country节点
#保存文件
tree.write("newnew.xml", encoding='utf-8')
结果
---新生成文件newnew.xml发现没有69对应内容,代表操作成功
<data1 age="19" title="CTO">
<country age="18" name="Liechtenstein">
<rank updated="yes">2</rank> #内容为2
<year>2023</year>
<gdppc>141100</gdppc>
<neighbor direction="E" name="Austria" />
<neighbor direction="W" name="Switzerland" />
</country>
<country name="Singapore">
<rank updated="yes">5</rank> #内容为5
<year>2026</year>
<gdppc>59900</gdppc>
<neighbor direction="N" name="Malaysia" />
</country>
</data1>
3、创建XML文档
(1) 以一行形式写入
from xml.etree import ElementTree as ET
root = ET.Element("famliy") # 创建根节点
son1 = ET.Element('son', {'name': '儿1'}) # 创建节点大儿子
son2 = ET.Element('son', {"name": '儿2'}) # 创建小儿子
grandson1 = ET.Element('grandson', {'name': '儿11'}) # 在大儿子中创建两个孙子
grandson2 = ET.Element('grandson', {'name': '儿12'})
son1.append(grandson1)
son1.append(grandson2)
root.append(son1) # 把儿子添加到根节点中
root.append(son1)
tree = ET.ElementTree(root)
tree.write('oooo.xml',encoding='utf-8', short_empty_elements=False)
结果
<famliy><son name="儿1"><grandson name="儿11"></grandson><grandson name="儿12"></grandson></son><son name="儿1"><grandson name="儿11"></grandson><grandson name="儿12"></grandson></son></famliy>
(2) 方式二
from xml.etree import ElementTree as ET
root = ET.Element("famliy") # 创建根节点
# son1 = ET.Element('son', {'name': '儿1'}) # 创建大儿子
son1 = root.makeelement('son', {'name': '儿1'})
# son2 = ET.Element('son', {"name": '儿2'})
son2 = root.makeelement('son', {"name": '儿2'}) # 创建小儿子
# grandson1 = ET.Element('grandson', {'name': '儿11'}) # 在大儿子中创建两个孙子
grandson1 = son1.makeelement('grandson', {'name': '儿11'})
# grandson2 = ET.Element('grandson', {'name': '儿12'})
grandson2 = son1.makeelement('grandson', {'name': '儿12'})
son1.append(grandson1)
son1.append(grandson2)
root.append(son1) # 把儿子添加到根节点中
root.append(son1)
tree = ET.ElementTree(root)
tree.write('oooo.xml',encoding='utf-8', short_empty_elements=False)
结果
<famliy><son name="儿1"><grandson name="儿11"></grandson><grandson name="儿12"></grandson></son><son name="儿1"><grandson name="儿11"></grandson><grandson name="儿12"></grandson></son></famliy>
(3) 方式三
from xml.etree import ElementTree as ET
root = ET.Element("famliy") # 创建根节点
son1 = ET.SubElement(root, "son", attrib={'name': '儿1'}) # 创建节点大儿子
son2 = ET.SubElement(root, "son", attrib={"name": "儿2"}) # 创建小儿子
grandson1 = ET.SubElement(son1, "age", attrib={'name': '儿11'}) # 在大儿子中创建一个孙子 #Sub创建节点,并append,干了两件事
grandson1.text = '孙子'
et = ET.ElementTree(root) #生成文档对象
et.write("test.xml", encoding="utf-8", xml_declaration=True, short_empty_elements=False)
结果
<?xml version='1.0' encoding='utf-8'?>
<famliy><son name="儿1"><age name="儿11">孙子</age></son><son name="儿2"></son></famliy>
由于原生保存的XML时默认无缩进,如果想要设置缩进的话, 需要修改保存方式:
from xml.etree import ElementTree as ET
from xml.dom import minidom
def prettify(elem):
"""将节点转换成字符串,并添加缩进。
"""
rough_string = ET.tostring(elem, 'utf-8') #换字符串
reparsed = minidom.parseString(rough_string) #格式化
return reparsed.toprettyxml(indent="\t") #加\t制表符
root = ET.Element("famliy") # 创建根节点
# 创建大儿子
# son1 = ET.Element('son', {'name': '儿1'})
son1 = root.makeelement('son', {'name': '儿1'})
# 创建小儿子
# son2 = ET.Element('son', {"name": '儿2'})
son2 = root.makeelement('son', {"name": '儿2'})
# 在大儿子中创建两个孙子
# grandson1 = ET.Element('grandson', {'name': '儿11'})
grandson1 = son1.makeelement('grandson', {'name': '儿11'})
# grandson2 = ET.Element('grandson', {'name': '儿12'})
grandson2 = son1.makeelement('grandson', {'name': '儿12'})
son1.append(grandson1)
son1.append(grandson2)
# 把儿子添加到根节点中
root.append(son1)
root.append(son1)
raw_str = prettify(root)
f = open("xxxoo.xml",'w',encoding='utf-8')
f.write(raw_str)
f.close()
结果
<?xml version="1.0" ?>
<famliy>
<son name="儿1">
<grandson name="儿11"/>
<grandson name="儿12"/>
</son>
<son name="儿1">
<grandson name="儿11"/>
<grandson name="儿12"/>
</son>
</famliy>
4、命名空间
from xml.etree import ElementTree as ET
ET.register_namespace('com',"http://www.company.com") #some name
# build a tree structure
root = ET.Element("{http://www.company.com}STUFF")
body = ET.SubElement(root, "{http://www.company.com}MORE_STUFF", attrib={"{http://www.company.com}hhh": "123"})
body.text = "STUFF EVERYWHERE!"
# wrap it in an ElementTree instance, and save as XML
tree = ET.ElementTree(root)
tree.write("page.xml",
xml_declaration=True,
encoding='utf-8',
method="xml")
结果
<?xml version='1.0' encoding='utf-8'?>
<com:STUFF xmlns:com="http://www.company.com"><com:MORE_STUFF com:hhh="123">STUFF EVERYWHERE!</com:MORE_STUFF></com:STUFF>
三、系统命令
可以执行shell命令的相关模块和函数有:
os.system
os.spawn*
os.popen* --废弃
popen2.* --废弃
commands.* --废弃,3.x中被移除
import commands
result = commands.getoutput('cmd')
result = commands.getstatus('cmd')
result = commands.getstatusoutput('cmd')
call
执行命令,返回状态码
import subprocess
ret = subprocess.call(["ls", "-l"], shell=False) #False 返回列表
ret = subprocess.call("ls -l", shell=True) #True 返回字符
check_call
执行命令,如果执行状态码是 0 ,则返回0,否则抛异常
subprocess.check_call(["ls", "-l"])
subprocess.check_call("exit 1", shell=True)
check_output
执行命令,如果状态码是 0 ,则返回执行结果,否则抛异常
import subprocess
subprocess.check_output(["echo", "Hello World!"])
subprocess.check_output("exit 1", shell=True)
subprocess.Popen(...)
用于执行复杂的系统命令
参数:
args:shell命令,可以是字符串或者序列类型(如:list,元组)
bufsize:指定缓冲。0 无缓冲,1 行缓冲,其他 缓冲区大小,负值 系统缓冲
stdin, stdout, stderr:分别表示程序的标准输入、输出、错误句柄
preexec_fn:只在Unix平台下有效,用于指定一个可执行对象(callable object),它将在子进程运行之前被调用
close_sfs:在windows平台下,如果close_fds被设置为True,则新创建的子进程将不会继承父进程的输入、输出、错误管道。
所以不能将close_fds设置为True同时重定向子进程的标准输入、输出与错误(stdin, stdout, stderr)。
shell:同上
cwd:用于设置子进程的当前目录
env:用于指定子进程的环境变量。如果env = None,子进程的环境变量将从父进程中继承。
universal_newlines:不同系统的换行符不同,True -> 同意使用 \n?startupinfo与createionflags只在windows下有效
将被传递给底层的CreateProcess()函数,用于设置子进程的一些属性,如:主窗口的外观,进程的优先级等等
创建目录
import subprocess
ret1 = subprocess.Popen(["mkdir","t1"])
ret2 = subprocess.Popen("mkdir t2", shell=True)
删除目录
import subprocess
ret1 = subprocess.Popen(["rm",'-rf',"t1"])
ret2 = subprocess.Popen("rm -rf t2", shell=True)
终端输入的命令分为两种:
输入即可得到输出,如:ifconfig
输入进行某环境,依赖再输入,如:python
在指的定目录操作(建目录)
import subprocess
obj = subprocess.Popen("mkdir t3", shell=True, cwd='/home/dev',)
在系统中执行python进入交互模式,输入信息
import subprocess
obj = subprocess.Popen(["python"], stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True)
obj.stdin.write("print(1)\n")
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)\n")
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)
四、高级的 文件、文件夹、压缩包 处理模块
1. shutil 使用
import shutil
shutil.copyfileobj
shutil.copyfileobj(fsrc, fdst[, length])
# 将文件内容拷贝到另一个文件中
# 一个目拷贝
import shutil
shutil.copyfileobj(open('xo.xml','r'), open('new.xml', 'w'))
shutil.copyfile()
# copy 内容
import shutil
shutil.copyfileobj(open('old.xml','r'), open('new.xml', 'w'))
#copy 文件
shutil.copyfile(src,dst)
shutil.copyfile('xo.xml','aa.xml')
# 拷贝文件
shutil.copyfile('f1.log', 'f2.log')
# 仅拷贝权限。内容、组、用户均不变(目标文件必须存在)
-rwxrwxrwx. 1 root root 110 6月 23 21:55 a.py #文件 a.py 777权限
-rw-r--r--. 1 root root 892 5月 10 22:57 ug.py #文件 ug.py 644权限
shutil.copymode('a.py', 'ug.py')
结果
-rwxrwxrwx. 1 root root 892 5月 10 22:57 ug.py #ug.py 变777,但内容没变
# 仅拷贝状态的信息,包括:mode bits, atime, mtime, flags
shutil.copystat('f1.log', 'f2.log')
# 拷贝文件和权限
import shutil
shutil.copy('f1.log', 'f2.log')
# 拷贝文件和状态信息
import shutil
shutil.copy2('f1.log', 'f2.log')
# 递归的去拷贝文件夹
shutil.copytree(src, dst, symlinks=False, ignore=None)
import shutil
shutil.copytree('folder1', 'folder2', ignore=shutil.ignore_patterns('*.pyc', 'tmp*'))
import shutil
shutil.copytree('f1', 'f2', symlinks=True, ignore=shutil.ignore_patterns('*.pyc', 'tmp*'))
# 递归的去删除文件
import shutil
shutil.rmtree('folder1')
# 递归的去移动文件,它类似mv命令,其实就是重命名。
import shutil
shutil.move('folder1', 'folder3')
shutil.make_archive(base_name, format,...)
创建压缩包并返回文件路径,例如:zip、tar
创建压缩包并返回文件路径,例如:zip、tar
•base_name: 压缩包的文件名,也可以是压缩包的路径。只是文件名时,则保存至当前目录,否则保存至指定路径,
如:www =>保存至当前路径
如:/Users/wupeiqi/www =>保存至/Users/wupeiqi/
•format: 压缩包种类,“zip”, “tar”, “bztar”,“gztar”
•root_dir: 要压缩的文件夹路径(默认当前目录)
•owner: 用户,默认当前用户
•group: 组,默认当前组
•logger: 用于记录日志,通常是logging.Logger对象
#将 /Users/wupeiqi/Downloads/test 下的文件打包放置当前程序目录
import shutil
ret = shutil.make_archive("wwwwwwwwww", 'gztar', root_dir='/Users/wupeiqi/Downloads/test')
#将 /Users/wupeiqi/Downloads/test 下的文件打包放置 /Users/wupeiqi/目录
import shutil
ret = shutil.make_archive("/Users/wupeiqi/wwwwwwwwww", 'gztar', root_dir='/Users/wupeiqi/Downloads/test')
2. zip方式
import zipfile
# 压缩
z = zipfile.ZipFile('laxi.zip', 'w')
z.write('test.xml')
z.write('xo.xml')
z.close()
# 解压 #解所有
z = zipfile.ZipFile('laxi.zip', 'r')
z.extractall()
z.close()
# 解压 #解单个
z = zipfile.ZipFile('laxi.zip', 'r')
z.extract('test.xml')
z.close()
3. tar 方式
import tarfile
# 压缩
tar = tarfile.open('your.tar','w')
tar.add('test.xml', arcname='test.log') #重命名压缩
tar.add('xo.xml', arcname='xo.log') #重命名压缩
tar.close()
# 解压 #解压所有
tar = tarfile.open('your.tar','r')
tar.extractall() # 可设置解压地址
tar.close()
#解压单个文件
tar = tarfile.open('your.tar','r')
obj = tar.getmember("test.log")
tar.extract(obj) # 可设置解压地址
tar.close()
五、 面向对像
http://www.cnblogs.com/wupeiqi/articles/5017742.html
实现邮件功能
封装对像,对像即self,加载一次,反复使用
什么时候用面向对像
当某一些函数具有相同参数时,将参数值一次封装
1. 面向对像实现操作SQL
#!/usr/bin/env python
#-*- coding:utf-8 -*-
# Author:Minghu Wang
class SQLHelper:
def fetch(self,sql):
print(obj.hhost)
print(obj.uusername)
print(obj.pwd)
print(sql)
def create(self,sql):
pass
def remove(self,nid):
pass
def modify(self,name):
pass
obj = SQLHelper() #创建对像,即self,self即对像的本身,self即等于obj
obj.hhost = "c1.salt.com" #封装到对像
obj.uusername = "alex" #封装到对像
obj.pwd = "123" #封装到对像
obj.fetch('select * from A') #使用对像的方法,先执行obj封装方法(即self),因为会把obj对像赋给self
结果:
c1.salt.com
alex
123
select * from A
2. self 是什么鬼?
self 是一个python自动给传的参数
那个对像执行方法,self就是谁
obj1.fetch('selec....') self=obj1
obj2.fetch('selec....') self=obj2
3. 构造方法
类中有一个特殊的方法__init__,类()自动被执行 (所以我们可以做初始化的功能放到这里)
----__init__方法使用
#!/usr/bin/env python
#-*- coding:utf-8 -*-
# Author:Minghu Wang
class SQLHelper:
def __init__(self,a1,a2,a3): #__init__等于obj(),即对像()执行时调用自动执行
print('自动执行init')
self.hhost = a1
self.uusername =a2
self.pwd = a3
def fetch(self,sql):
print(obj.hhost)
print(obj.uusername)
print(obj.pwd)
print(sql)
def create(self,sql):
pass
def remove(self,nid):
pass
def modify(self,name):
pass
obj = SQLHelper('c1.salt.com','alex',123) #类()自动执行__init__方法,所以我们可以对__init__进行操作
obj.fetch('select * from A') #使用对像的方法
结果:
自动执行init
c1.salt.com
alex
123
select * from A
3. 类的多次封装
#类的二次封装,多层类调用,嵌套
class c1:
def __init__(self,name,obj):
self.name = name
self.obj = obj
class c2:
def __init__(self,name,age):
self.name = name
self.age = age
def show(self):
print(self.name)
c2_obj = c2('aa',11)
c1_obj = c1("alex",c2_obj) #将c2_obj对像封装到c1_obj对像
print(c1_obj.obj.age) #obj.age调用c2类的方法的age变量
结果:
11
#类的三次封装,嵌套调用
class c1:
def __init__(self,name,obj):
self.name = name
self.obj = obj
class c2:
def __init__(self,name,age):
self.name = name
self.age = age
def show(self):
print(self.name)
print('show')
class c3:
def __init__(self,a1):
self.money = 123
self.aaa = a1
c2_obj = c2('aa',11)
# c2_obj 是c2 类型
#-- name = 'aa'
#-- age = 11
c1_obj = c1("alex",c2_obj) #将c2_obj对像封装到c1_obj对像
# c1_obj 是c1 类型
# -- name = 'alex'
# -- obj = c2_obj
c3_obj = c3(c1_obj)
# 使用c3_obj执行show方法
print(c3_obj.aaa.name)
print(c3_obj.aaa.obj.age)
c3_obj.aaa.obj.show()
结果:
alex
11
aa
show
#类的三次封装,嵌套调用
class c1:
def __init__(self,name,obj):
self.name = name
self.obj = obj
class c2:
def __init__(self,name,age):
self.name = name
self.age = age
def show(self):
print(self.name)
return 123
class c3:
def __init__(self,a1):
self.money = 123
self.aaa = a1
c2_obj = c2('aa',11)
# c2_obj 是c2 类型
#-- name = 'aa'
#-- age = 11
c1_obj = c1("alex",c2_obj) #将c2_obj对像封装到c1_obj对像
# c1_obj 是c1 类型
# -- name = 'alex'
# -- obj = c2_obj
c3_obj = c3(c1_obj)
# 使用c3_obj执行show方法
# print(c3_obj.aaa.name)
# print(c3_obj.aaa.obj.age)
ret = c3_obj.aaa.obj.show()
print(ret)
结果
aa
123
4. 面向对像--继承
#继承是把父类的代码复制过来一份
class F1: #父类,基类
def show(self):
print('show')
def foo(self):
print(self.name)
class F2(F1): #子类,派生类
def __init__(self,name):
self.name = name
def bar(self):
print('bar')
def show(self):
print('F2.show')
obj = F2('alex') #创建对像obj,给F2传值
#obj.show()
obj.foo() #执行对像调用foo方法。执行是F1的foo
结果
alex