目录
1.open函数打开文件
使用 open 函数创建一个文件对象,read 方法来读取数据,write 方法来写数据
语法:fileObject = open(filename, mode)
filename文件路径
mode取值:
- "r":为了读打开一个文件
- "w":为了写打开一个文件,如果文件已经存在则覆盖
- "a":为了写打开一个文件,从文件末尾追加写入
- "rb":为读取二进制数据打开文件
- "wb":为写入二进制数据打开文件
- "ab":追加写入二进制数据
python
file1 = open("scores.txt", "r")
# 在 filename 前加上 r 表示将反斜线\看做普通的字符,使其没有其他功能
file2 = open(r"c:\pybook\scores.txt", "r")
# 如果没有 r 前缀,使用转义序列
file3 = open("c:\\pybook\\scores.txt", "r")
2.文件对象读写数据和关闭
open函数创建了一个文件对象,这是_io.TextIOWrapper类的一个实例。这个类包含了读写数据和文件关闭的方法。
特别说明:
- readline()是读取当前行中还未读取的内容,返回字符串。这个行指以换行符\n 结尾之前的内容
- readlines()是读取剩下所有未读取的内容,返回列表,列表的每一个元素时每行未读取的字符串
- print 函数会自动插入换行符\n,而 write 方法需要显式地添加一个换行符号\n 用来换行写数据
- close方法必须被调用,特别是写文件时,忘记close可能导致文件内容无法写入
python
def main():
outfile = open("Presidents.txt", "w")
outfile.write("QingHui\t")
outfile.write("ZhangSan\n")
outfile.write("XiaoWang\t")
outfile.write("DaBing\n")
outfile.write("Others")
outfile.close()
file2 = open("Presidents.txt", "r")
string1 = file2.read(10)
print(string1) # QingHui Zh
string3 = file2.readline()
print(string3) # angSan
string4 = file2.readlines() # ['XiaoWang\tDaBing\n', 'Others']
print(string4)
file2.close()
main()
按行读取文件全部数据
python
# 法一
infile = open("Presidents.txt", "r")
all_data = []
line = infile.readline()
while line != '':
all_data.append(line)
line = infile.readline()
print(all_data)
# 法二
infile = open("Presidents.txt", "r")
all_data = []
for line in infile:
all_data.append(line)
print(all_data)
"""
['QingHui\tZhangSan\n', 'XiaoWang\tDaBing\n', 'Others\n', '\n', '\n']
['QingHui\tZhangSan\n', 'XiaoWang\tDaBing\n', 'Others\n', '\n', '\n']
"""
简洁读写文件
with open(参数) as file, 自动关闭文件
python
filepath = r"D:\test\1.txt"
with open(filepath, "r") as file:
for line in file:
print(line, end="")
print()
with open(filepath, "rb") as file:
for line in file:
line = line.decode("gbk", "ignore")
print(line, end="")
print()
读写数值数据
由于文本文件中的数据都是字符串类型,所以在进行数值数据的读写的时候都要进行相应的数据类型转换。为了正确地读出文件中的数字,利用" "或者\n 的空白符来分隔数字。复杂一点的需要使用正则表达式。
python
from random import randint
def main():
outfile = open("Numbers.txt", "w")
for i in range(100):
outfile.write(str(randint(0, 9)) + " ")
outfile.close()
infile = open("Numbers.txt", "r")
s = infile.read()
numbers = [eval(x) for x in s.split()]
for number in numbers:
print(number, end = " ")
infile.close()
main()
3.文本文件和二进制文件的区别
参考这篇文章中《2.文本文件与二进制文件的区别》
4.编码和解码
读写文本文件时
- 编码就是将文本模式变成二进制模式。在向一个文本文件写入指定内容时,会将文本内容按指定编码类型编码为二进制,然后放在文件中。
- 解码就是二进制模式变为文本模式。在从一个文本文件读取内容时,会将读取到的二进制内容按指定编码类型解码为字符串。
打开文件时,如果不指定编码方式,则默认utf-8,不过也可以使用encoding参数指定编码方式。
注意写入文件时用什么编码方式,读取时也最好用什么编码方式,这样保证内容能正确读取到,否则会出现UnicodeDecodeError或者乱码。
python
w_file = open("data.txt", "w", encoding="gbk")
w_file.write("你好中国")
w_file.close()
# 当用不同的编码方式读取文件内容时会报错或者出现乱码
r_file = open("data.txt", "r", encoding="utf-8")
for line in r_file:
print(line)
r_file.close()
"""
会报错:UnicodeDecodeError:
'utf-8' codec can't decode byte 0xc4 in position 0: invalid continuation byte
"""
如何手动查看文本文件的编码方式
如何手动修改文本文件的编码方式:文件另存为时设置
读写二进制文件时
读写二进制文件时,在用open函数创建文件对象,不能使用encoding函数,否则会"ValueError: binary mode doesn't take an encoding argument"。而是在write函数前对需要写入的字符串内容进行encode,或者在read读到的内容后进行decode。
python
# 写入数据
file = open("data.txt", "wb")
data = "hello 中国" # 字符串内容
file.write(data.encode("utf-8")) # 将字符串内容按utf-8编码为二进制写入到文件中
# 这个时候去查看"data.txt"的编码就可以看到是 utf-8 编码了
file.close()
# 读取数据
file = open("data.txt", "rb")
txt = file.read().decode("utf-8")
print(type(txt)) # <class 'str'>
print(txt) # hello 中国
file.close()
5.文件指针位置
在创建文件时,文件指针位置在起始位置,在第 0 行的前面。每次读或写时,文件指针位置都会前移。
可以使用seek主动调整文件指针位置。
- seek(arg1, arg2) 第一个参数是偏移量,第二个参数表示模式,0 表示开头,1 为中间,2 为末尾
- file.seek(16, 0) 表示指针从开头的第 16 个字符起开始
- file.seek(0, 0) 文件指针跳转到开头
tell 方法获取文件指针当前的位置
python
file = open("data.txt", "w")
file.write("1234567\n")
file.write("89\n")
file.write("xyz\n")
file.close()
file = open("data.txt", "r")
print(f"index={file.tell()}\n") # 1
for i in range(12):
ret = file.read(1)
print(f"value=({ret})") # 1
print(f"index={file.tell()}\n") # 1
file.close()
运行结果
bash
index=0
value=(1)
index=1
value=(2)
index=2
value=(3)
index=3
value=(4)
index=4
value=(5)
index=5
value=(6)
index=6
value=(7)
index=18446744073709551624
value=(
)
index=9
value=(8)
index=10
value=(9)
index=18446744073709551628
value=(
)
index=13
value=(x)
index=14
注意在换行符号"\n"处,文件指针跳动了两个单位,是因为windows下"\n"会自动变成"\r\n"。
6.文件缓存区与flush()方法
write 是写入内存的缓冲区,没有实时写入
等到 file.close()后再集中处理,或者缓冲区满了就真正写入
缓冲区的作用:磁盘是有寿命的,读取 or 写入一次寿命就会减少
python
import time
file = open("data.txt", "w")
file.write("abcdefg")
file.flush() # 刷新,实时写入
# 此时查看data.txt中会有数据"abcdefg",否则会等到file.close() 才有数据
# 有了这个语句就不怕忘记写 file.close()这个了
time.sleep(30)
file.close() # 文件是在文件关闭后才能写入,很重要
end