文件、深浅拷贝

文件

1、open()方法
open()方法用于打开一个文件,并返回文件对象,在对文件进行处理的过程中都需要使用这个函数,如果文件无法打开,则抛出OSError

注意:使用open方式一定要保证关闭文件对象,即调用close()方法

完整的语法定义格式:open(file, mode='r', buffering=-1, encoding=None, errors=None, newline=None, closefd=True, opener=None)

参数说明:
	file:必须,文件路径(绝对或相对路径)
	mode:文件打开模式,默认为r
	buffering:设置缓冲
	encoding:一般使用utf-8,在windows系统中,如果文件是以utf-8保存的,操作系统的默认编码是gbk,直接打开会报错,需要将encoding设置成utf-8;如果文件是以gbk保存的,可以直接打开,
	errors:报错级别
	newline:区分换行符
	closefd:传入的文件类型
	opener: 设置自定义开启器,开启器的返回值必须是一个打开的文件描述符

2、模式介绍

模式 说明
r 以只读的方式打开文件,文件的指针会在文件的开头,这是默认的模式
w 打开一个文件只用于写入,如果该文件已存在,则删除文件内容,从开头开始写入,如果该文件不存在则创建一个新文件
a 打卡一个文件用于追加,如果该文件已存在,文件指针将会放在文件的结尾。也就是说,新的内容将会被写入到已有内容之后。如果该文件不存在,创建新文件进行写入
r+ 以只读的方式打开文件,从开头读取,从文件末尾写入
w+ 打开一个文件只用于写入和读取,如果该文件已存在,则删除文件内容,从开头开始写入,如果该文件不存在则创建一个新文件,写入和读取的光标位置一样
a+ 打卡一个文件用于追加和读取,如果该文件已存在,文件指针将会放在文件的结尾。也就是说,新的内容将会被写入到已有内容之后。如果该文件不存在,创建新文件进行写入,读取和写入都是从文件的末尾开始
# r:读模式,文件不存在报错
# f = open('小重山1',mode='r',encoding='utf-8')
# data = f.read()
# print(data)
# f.close()


# w:写模式,文件不存在创建文件,文件存在删除内容再写入
# f = open('小重山2',mode='w',encoding='utf-8')
# f.write('hello')
# f.close()


# a: 追加模式,文件不存在则创建文件,文件存在则从末尾写入内容
# f = open('小重山3',mode='a',encoding='utf-8')
# f.write('hello')
# f.close()


# r+: 可读可写,从开头读,从末尾写入
# f = open('小重山3',mode='r+',encoding='utf-8')
# print(f.readline())    # hellohellofasdf
# f.writelines('fasdf')


# w+ :可读可写,读写光标位置一样
# f = open('小重山3', mode='w+', encoding='utf-8')
# f.write('duyuzhi')
# print(f.readline())  # 空白
# f.seek(0)
# print(f.readline())  # duyouzhi


# a+:可读可写,读写光标位置一样,在文件末尾
# f = open('小重山3', mode='a+', encoding='utf-8')
# print(f.readline())  # 空白
# f.write('fffff')    # duyuzhifffff
# f.seek(0)
# print(f.readline())

3、迭代器,每执行一次,从磁盘读取一次

f = open('小重山1', mode='r', encoding='utf8')
for v in f:
	print(v.strip())

4、文件的内置函数
read([size]) -> str 从文件读取指定的字符数(文本模式)或字节数(二进制模式),如果未给定参数size或size为负数,则读取所有内容

f = open('小重山1', mode='r', encoding='utf8')
print(f.read(5))  # 读取5个字符
print(f.read())  # 读取整个文件

readline([size]) -> str 方法用于从文件读取整行,包括 "\n" 字符。如果指定了一个非负数的参数,则返回指定大小的字节数,包括 "\n" 字符。

f = open('小重山1', mode='r', encoding='utf8')
print(f.readline().strip())  # 昨夜寒蛩不住鸣。
print(f.readline().strip())  # 惊回千里梦,已三更。

readlines() -> list 读取所有行并返回列表

f = open('小重山1',mode='r',encoding='utf8')
list1 = f.readlines()
print(list1)    # 返回一个列表

tell() -> int 返回光标所在的位置
seek() -> int 移动文件读取指针到指定位置

f = open('小重山1', mode='r', encoding='utf8')
print(f.tell())  # 0
print(f.read(9))  # 昨夜寒蛩不住鸣。
print(f.tell())  # 26
f.seek(0)
print(f.tell())  # 0
print(f.read(1))    # 昨

flush() -> 将缓冲区中的数据立刻写入文件,同时清空缓冲区,不需要是被动的等待输出缓冲区写入

#terminal上操作:
# f = open('小重山1','w')
# f.write('hello \n')
# f.flush()

# 应用:进度条
import sys,time
for i in range(30):
	sys.stdout.write('*')
	sys.stdout.flush()
	time.sleep(0.2)

truncate() -> int从文件的首行首字符开始截断,截断文件为 size 个字符,无 size 表示从当前位置截断;截断之后后面的所有字符被删除,其中 windows 系统下的换行代表2个字符大小

f = open('小重山1','a')
print(f.truncate())    # 截取所有字符
print(f.truncate(5))    # 截取前50个字符
f.close()

5、with语句

with open('log1') as obj1, open('log2') as obj2:
pass

深浅拷贝

# 赋值,完全一样
names_class1 = ['张三', '李四', '王五', '赵六', [1, 2, 3]]
names_class2 = ['张三', '李四', '王五', '赵六', [1, 2, 3]]
names_class3 = names_class1

# 比较1和2的内容以及地址值
print(names_class1 == names_class2,id(names_class1) == id(names_class2))  # True,False
print(names_class1[4] == names_class2[4],id(names_class1[4]) == id(names_class2[4]))  # True,False

# 比较1和3的内容和地址值
print(names_class1 == names_class3,id(names_class1) == id(names_class3))  # True,True
print(names_class1[4] == names_class3[4],id(names_class1[4]) == id(names_class3[4]))  # True,True


# 修改names_class1的内容,
names_class1[0] = '张三'
print(names_class1[0],names_class3[0],id(names_class1) == id(names_class3))  # 张三 张三 True

names_class1[4][2] = 4
print(names_class1[4][2],names_class3[4][2],id(names_class1) == id(names_class3))  # 4 4 True

# 浅拷贝,只拷贝最外面一层(即最外一层的地址值不一样,里面的都一样)
a = [[1, 2], 3, 4]
b = a[:]  # b=a.copy()

print(id(a), id(b), id(a) == id(b))  # 1740465625032 1740465625160 False
print('*************')
print(id(a[0]) == id(b[0]), id(a[1]) == id(b[1]), id(a[2]) == id(b[2]))  # True True True

print('____________________修改第2层_______________________')
b[0][0] = 8
print(id(a[0]) == id(b[0]))  # True
print(id(a[0][0]) == id(b[0][0]), id(a[0][1]) == id(b[0][1]))  # True,True

print('____________________修改第1层_______________________')
b[1] = 5
print(a[1], b[1], id(a[1]) == id(b[1]))  # 3 5 False

# # 深拷贝,拷贝多层(即内层的可变类型地址值都不一样)
from copy import deepcopy

a = [[1, 2], 3, 4]
b = deepcopy(a)
print(id(a), id(b), id(a) == id(b))  # 1740465625032 1740465625160 False
print('*************')
print(id(a[0]) == id(b[0]), id(a[1]) == id(b[1]), id(a[2]) == id(b[2]))  # False True True

print('____________________修改第2层_______________________')
b[0][0] = 8
print(id(a[0]) == id(b[0]))  # False
print(id(a[0][0]) == id(b[0][0]), id(a[0][1]) == id(b[0][1]))  # False,True

print('____________________修改第1层_______________________')
b[1] = 5
print(a[1], b[1], id(a[1]) == id(b[1]))  # 3 5 False
posted @ 2023-03-27 22:15  duuuu  阅读(96)  评论(0)    收藏  举报