第二模块 函数&模块
第一模块主要是学习python基础知识,从第二模块开始就可以通过程序去解决工作中实际的问题。
第二模块的内容主要包含两大部分:
函数
一个用于专门实现某个功能的代码块(可重用)。
-
内置函数
len、bin、oct、hex...等
-
自定义函数
# 定义了一个函数,相当于封装了一个功能代码块 def send_email(): # 写了10行代码,实现了发送邮件。 pass goods = [ { "name": "电脑", "price": 1999}, { "name": "鼠标", "price": 10}, { "name": "游艇", "price": 20}, { "name": "美女", "price": 998} ] for index in range(len(goods)): item = goods[index] print(index + 1, item['name'], item['price']) # 调用并执行函数 send_email() while True: num = input("请输入要选择的商品序号(Q/q):") # "1" if num.upper() == "Q": break if not num.isdecimal(): print("用输入的格式错误") break num = int(num) send_email() if num > 4 or num < 0: print("范围选择错误") break target_index = num - 1 choice_item = goods[target_index] print(choice_item["name"], choice_item['price']) send_email()
模块
集成了很多功能的函数集合。
-
内置模块,是Python内部已经定义好的功能集合。
import random # 导入内置模块 num = random.randint(0,19)
import decimal # 导入内置模块 v1 = decimal.Decimal("0.1") v2 = decimal.Decimal("0.2") v3 = v1 + v2 print(v3)
-
第三方模块,网上下载别人写好的模块(功能集合)。
-
自定义模块
day09 文件操作相关
课程目标:掌握基于Python对文件相关操作。
课程概要:
- 文件操作
- 文件夹和路径
- csv格式文件
- ini格式文件
- xml格式文件
- excel文件
- 压缩文件
注意:每种文件格式包含很多相关操作,大家在学习的过程中只要掌握知识点的用法,参考笔记可以实现相关的练习即可,不必背会(在企业开发过程中也是边搜边实现的)。
1. 文件操作
在学习文件操作之前,先来回顾一下编码的相关以及相关数据类型的知识。
-
字符串类型(str),在程序中用于表示文字信息,本质上是unicode编码中的二进制。
name = "轩小陌"
-
字节类型(bytes)
-
可表示文字信息,本质上是utf-8/gbk等编码的二进制(对unicode进行压缩,方便文件存储和网络传输。)
name = "轩小陌" data = name.encode('utf-8') print(data) # b'\xe6\xad\xa6\xe6\xb2\x9b\xe9\xbd\x90' result = data.decode('utf-8') print(result) # "轩小陌"
-
可表示原始二进制(图片、文件等信息)
-
1.1 读文件
-
读文本文件
# 1.打开文件 # - 路径: # 相对路径:'info.txt' # 绝对路径:'/Users/xuanxiaomo/PycharmProjects/day09/info.txt' # - 模式 # rb,表示读取文件原始的二进制 r:读(read) b:二进制(binary) # 1.打开文件 file_object = open('info.txt', mode='rb') # 2.读取文件内容,并赋值给data data = file_object.read() # 3.关闭文件 file_object.close() print(data) # b'alex-123\n\xe6\xad\xa6\xe6\xb2\x9b\xe9\xbd\x90-123' text = data.decode("utf-8") print(text)
# - 模式 # rt,表示读取文件的文本数据 r:读(read) t:文本内容(text) # 1.打开文件 file_object = open('info.txt', mode='rt', encoding='utf-8') # 2.读取文件内容,并赋值给data data = file_object.read() # 3.关闭文件 file_object.close() print(data)
-
读图片等非文本内容文件。
file_object = open('a1.png', mode='rb') data = file_object.read() file_object.close() print(data) # \x91\xf6\xf2\x83\x8aQFfv\x8b7\xcc\xed\xc3}\x7fT\x9d{.3.\xf1{\xe8\...
注意事项:
-
路径
-
相对路径:如果在python文件中使用了相对路径,那么在运行python解释器的时候,要确保相对路径的文件放在与解释器同一个路径下,否则解释器将无法找到该文件。
-
绝对路径
# 1.打开文件 file_object = open('/Users/xuanxiaomo/PycharmProjects/day09/info.txt', mode='rt', encoding='utf-8') # 2.读取文件内容,并赋值给data data = file_object.read() # 3.关闭文件 file_object.close()
windows系统中写绝对路径容易出问题:
# 单纯输入绝对路径'C:\new\info.txt'会报错,因为系统会将识别\n识别成换行符: file_object = open('C:\new\info.txt', mode='rt', encoding='utf-8') # 第一种解决办法:将路径中的'\'全部改成'\\': file_object = open('C:\\new\\info.txt', mode='rt', encoding='utf-8') # 第二种解决办法:在路径前面加上字母'r': file_object = open(r'C:\new\info.txt', mode='rt', encoding='utf-8')
-
-
读文件时,如果文件不存在程序会报错,错误信息如下:
Traceback (most recent call last): File "/Users/xuanxiaomo/PycharmProjects/day09/2.读文件.py", line 2, in <module> file_object = open('infower.txt', mode='rt', encoding='utf-8') FileNotFoundError: [Errno 2] No such file or directory: 'info.txt'
因此,我们在打开和读取文件前,可以先判断路径是否存在,如果存在,再进行打开和读取操作:
import os file_path = "/Users/xuanxiaomo/PycharmProjects/day09/info.txt" exists = os.path.exists(file_path) if exists: # 1.打开文件 file_object = open('info.txt', mode='rt', encoding='utf-8') # 2.读取文件内容,并赋值给data data = file_object.read() # 3.关闭文件 file_object.close() print(data) else: print("文件不存在")
1.2 写文件
-
写文本文件
# 1.模式:wb(要求写入的内容是字节类型) file_object = open("t1.txt", mode='wb') # 2.写入内容 file_object.write("轩小陌".encode("utf-8")) # 3.文件关闭 file_object.close()
# 1.模式:wt(要求写入的内容是文本内容) file_object = open("t1.txt", mode='wt', encoding='utf-8') # 2.写入内容 file_object.write("轩小陌") # 3.文件关闭 file_object.close()
-
写图片等文件
# a1图片文件的内容读取出来: f1 = open('a1.png',mode='rb') content = f1.read() f1.close() # 将上面读取到的a1文件的内容写入到a2文件中: f2 = open('a2.png',mode='wb') f2.write(content) f2.close()
基础案例:
# 案例1:用户名、密码注册并写入文件中
user = input("请输入用户名:")
pwd = input("请输入密码:")
data = "{}-{}".format(user, pwd)
file_object = open("files/info.txt", mode='wt', encoding='utf-8')
# 用open打开文件时,如果路径下文件不存在,则会创建一个文件
file_object.write(data)
file_object.close()
# 案例2:多用户注册
file_object = open("files/info.txt", mode='wt', encoding='utf-8')
while True:
user = input("请输入用户名:")
if user.upper() == "Q":
break
pwd = input("请输入密码:")
data = "{}-{}\n".format(user, pwd)
file_object.write(data)
file_object.close()
注意:open打开文件时,w写入模式会默认先清空文件内容;再在文件中写入内容。所以为了不要清空文件内容,只在一开始的时候打开文件即可,不要重复打开文件。
进阶案例:(内容超前)
利用Python向某个网址发送请求并获取结果(通过第三方的模块)
下载第三方模块
pip install requests
# 如果上述方式安装不成功,可以先在python安装路径中找到pip的绝对路径,再进行安装: /Library/Frameworks/Python.framework/Versions/3.9/bin/pip3 install requests
使用第三方模块
import requests res = requests.get(url="网址") print(res)
# 案例1:去网上下载文本,文本信息写入文件。
import requests
res = requests.get(
url="https://movie.douban.com/j/search_subjects?type=movie&tag=%E7%83%AD%E9%97%A8&sort=recommend&page_limit=20&page_start=20",
headers={
"User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4280.88 Safari/537.36"
}
)
# res里面存的是服务器返回的所有信息,包括响应头,响应状态码等
# res.content返回网页的字节码(原始二进制信息bytes)
file_object = open('files/log1.txt', mode='wb')
file_object.write(res.content)
file_object.close()
# 案例2:去网上下载一张图片,图片写入本地文件。
import requests
res = requests.get(
url="https://hbimg.huabanimg.com/c7e1461e4b15735fbe625c4dc85bd19904d96daf6de9fb-tosv1r_fw1200",
headers={
"User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4280.88 Safari/537.36"
}
)
# res里面存的是服务器返回的所有信息,包括响应头,响应状态码等
# res.content返回网页的字节码(原始二进制信息bytes)
file_object = open('files/picture.png', mode='wb')
file_object.write(res.content)
file_object.close()
1.3 文件打开模式
上文我们基于文件操作基本实现了读、写的功能,其中涉及的文件操作模式:rt、rb、wt、wb,其实在文件操作中还有其他的很多模式。
========= ===============================================================
Character Meaning
--------- ---------------------------------------------------------------
'r' open for reading (default)
'w' open for writing, truncating the file first
'x' create a new file and open it for writing
'a' open for writing, appending to the end of the file if it exists
'b' binary mode
't' text mode (default)
'+' open a disk file for updating (reading and writing)
The default mode is 'rt' (open for reading text).
关于文件的打开模式常见应用有:
-
只读:
r
、rt
、rb
(常用)- 文件存在,则读
- 文件不存在,则报错
-
只写:
w
、wt
、wb
(常用)- 文件存在,则清空再写入
- 文件不存在,则创建后再写入
-
只写:
x
、xt
、xb
(几乎不用)- 文件存在,则报错
- 文件不存在,则创建后再写入。
-
只写:
a
、at
、ab
【尾部追加】(常用)- 文件存在,则在尾部追加。
- 文件不存在,则创建后再写入。
-
读写
-
r+、rt+、rb+,注意:读和写的起始位置都要看目前的光标位置
file_object = open('info.txt', mode='rt+') # 读取内容 data = file_object.read() print(data) # 假设文件中原文本内容为:root-123 # 写入内容 file_object.write("alex") file_object.close() # 先读后写,写入的位置默认为读取之后的位置
file_object = open('info.txt', mode='rt+') # 写入内容 file_object.write("alex") # 读取内容 data = file_object.read() print(data) # 输出结果:-123 file_object.close() # 先写后读,写入的位置默认为文件开头,读取的位置为写入文本之后的位置
-
w+、wt+、wb+,注意:读的起始位置要看目前光标位置,写的起始位置默认为文件开头(因为w模式每次写入均会先清空文件)
file_object = open('info.txt', mode='wt+') # 读取内容 data = file_object.read() print(data) # 写入内容 file_object.write("你好呀") # 将光标位置重置到起始位置 file_object.seek(0) # 读取内容 data = file_object.read() print(data) # 输出结果:你好呀 file_object.close()
-
x+、xt+、xb+,与w+、wt+、wb+类似,唯一不同是x模式下每次都会创建新文件。
-
a+、at+、ab+,默认光标位置是文件末尾
file_object = open('info.txt', mode='at+') # 写入内容 file_object.write("轩小陌") # 将光标位置重置起始 file_object.seek(0) # 读取内容 data = file_object.read() print(data) # 输出结果:原文本内容+轩小陌 file_object.close()
-
案例:多用户注册
file_object = open('files/account.txt', mode='a')
# 相比上面用w模式打开文件,用a模式打开文件可以保证文件内原数据不会被清空
while True:
user = input("用户名:")
if user.upper() == "Q":
break
pwd = input("密码:")
data = "{}-{}\n".format(user, pwd)
file_object.write(data)
file_object.close()
1.4 常见功能
在上述对文件的操作中,我们只使用了write和read来对文件进行读写,其实在文件操作中还有很多其他的功能来辅助实现更好的读写文件的内容。
1.4.1 read:读
-
读所有【常用】
f = open('info.txt', mode='r',encoding='utf-8') data = f.read() f.close()
f = open('info.txt', mode='rb') data = f.read() f.close()
-
读n个字符(字节)【有时会用】
f = open('info.txt', mode='r', encoding='utf-8') data = f.read(1) # 读1个字符 f.close() print(data)
f = open('info.txt', mode='rb') data = f.read(3) # 读3个字节 f.close() print(data, type(data)) # 输出结果:b'\xe6\xad\xa6' <class 'bytes'>
1.4.2 readline:读一行内容
f = open('info.txt', mode='r', encoding='utf-8')
v1 = f.readline() # 读第一行内容
v2 = f.readline() # 读第二行内容
...
f.close()
1.4.3 readline加强版:for循环读取文件每行内容
f = open('info.txt', mode='r', encoding='utf-8')
for line in f:
print(line.strip())
f.close()
1.4.4 readlines:读所有行内容,并将每行内容作为列表的一个元素
f = open('info.txt', mode='rb')
data_list = f.readlines()
print(data_list)
f.close()
1.4.5 write:写
f = open('info.txt', mode='a',encoding='utf-8')
f.write("轩小陌")
f.close()
f = open('info.txt', mode='ab')
f.write( "轩小陌".encode("utf-8") )
f.close()
1.4.6 flush:将缓冲区的内容刷到硬盘
f = open('info.txt', mode='a',encoding='utf-8')
while True:
f.write("轩小陌")
# write不是直接写到硬盘上,而是先写在缓冲区,系统会不定时将缓冲区的内容刷到硬盘。
f.flush() # 使用flush()可以保证写入的内容立即刷到硬盘上
f.close()
1.4.7 seek:将光标移动到指定字节的位置
f = open('info.txt', mode='r+', encoding='utf-8')
f.seek(3)
f.write("轩小陌")