字符编码,文件处理几种语法,with嵌套,copy的简单使用

什么是字符编码
    人类的语言   ----- 翻译    -----    二进制
    翻译的过程就称之为字符编码

    保存不是目的 能取出来才是目的
    二进制  --------- 翻译 ------ 人类的语言

    要想保存翻译的结果则保证采用相同的规范也就是字符编码

    ascII   一个字符占 一个字节
    GBK  中文使用两个字节 英文使用一个字节
    unicode 支持任何国家的语言,使用两个字节存储任意符号
    utf-8 可以将其看做是unicode的升级版,一个英文占1个字节 中文占三个字节,

    UTF-8 使用场景:
        1.当我们需要将数据基于网络进行发送时则必须将数据转成二进制
        GBK,UTF-8。。。都可以,但是由于UTF-8 兼容网并且节省空间,所以更推荐使用UTF-8

        2.当你需要将数据从内存写到硬盘,也推荐使用UTF-8

    乱码的发生的两种情况******
    1.存的时候使用的编码与取的时候不同,
    2.存的时候,出现了编码表中不存在的字符,例如既有英文,又有中文,但是采取了asc来编码

    如何保证不乱码******
    1.存取一致
    2.使用兼容万国的编码表

    解释器在读取py文件后需要识别语法,当在定义字符串变量时又涉及到编码问题
    py2中默认采用asc 也可以使用coding来指定,但也有乱码的可能
                                            当coding为gbk 而输出字符时采用utf-8
    py3 中默认就是unicode   并且coding也只能修改前两阶段解码过程,无法修改定义变量的编码

    ******
    encode 将unicode ----- 翻译 -----某种指定格式的二进制如utf-8
    decode 将某种指定格式的二进制如utf-8   --- 翻译  ---   unicode

    encode的使用场景  ******
    1.需要文本写入到硬盘时
    2.需要将文本基于网络发送时

文件处理
    文件是操作系统提供一套虚拟接口 用于简化对于硬盘的操作,一个文件就代表硬盘上的一段二进制数据
    学习文件处理是为了将数据永久保存

    基本形式
    1.打开文件语法1
    f = open(r"文件路径",mode="rt",encoding="utf-8")
    f.read()
    #f.write()
    f.close()

    2.语法2
    with open(r"文件路径",mode="rt",encoding="utf-8") as f:
        pass

    打开文件的模式
    默认为t模式 即文本操作模式
    r  == rt  只读文本
    w  == wt  只写文本
    a  == at  追加写文本
    无论是读还是写 都需要指定编码方式,如果不指定 windows默认为GBK linux默认UTF-8
    操作数据都是字符为单位

    a 和 w 都是写入模式,如果文件不存在都会创建新文件
    不同的是 w会清空源文件  a不会情况且会将光标移动文件末尾

文本模式:

必须与'r','w'.'a'连用:

with open("userdb.txt","r",encoding="utf-8") as f:
     data = f.read()

 name = input("请输入用户名:").strip()
 with open("userdb.txt","wt",encoding="utf-8") as f:
    f.write(data)
     f.write("\n")
     f.write(name+"\n")

 name = input("name:").strip()
 with open("userdb.txt",mode="at",encoding="utf-8") as f:
     f.write(name+"\n")

b表示字节模式
    与文本相同在于 都必须与r、w、a连用
    rb 只读字节模式
    wb 只写字节模式
    ab 追加只写字节模式
b模式可以操作任意类型的文件
注意:
    1.b模式不允许设置编码参数
    2.读写数据都以字节为单位

事例:

with open("2.文本模式回顾.mp4",mode="rb")as f:
     data = f.read(1024*1024)
     print(data)
     print(type(data))
      print(data.decode("")) 

 with open("userdb2.txt", mode="wb")as f:
     f.write("123".encode("utf-8"))
     print(type("123".encode("utf-8")))

with open("userdb2.txt", mode="ab")as f:
    f.write("123".encode("utf-8"))
    print(type("123".encode("utf-8")))

+ 表示可读可写模式
也不能单独使用
r+  ==  r+t  直接写入 会把元数据覆盖掉
w+  ==  w+t  打开就清空 所以读不到
a+  ==  a+t  打开就移动光标到末尾 也读不到

 可读可写字节模式
r+b    直接写入 会把元数据覆盖掉
w+b    打开就清空 所以读不到
a+b    打开就移动光标到末尾 也读不到
仅仅是单位不同

 每一个都有问题 所以可读可写并不常用

 with open("log.txt",mode="r+",encoding="utf-8") as f:

      print(f.read())
     f.write("abc")

copy:

复制文件?
从源文件读取 写入到新文件中

1.打开源文件

source_f = open("作业基础版.py","rb")

2.打开目标文件

dst_f = open("作业副本.py","wb")

 

3.从源文件读取数据 写入到目标文件

 data = source_f.read()
dst_f.write(data)

 source_f.close()
dst_f.close()

4.并列打开多个文件 可以用逗号隔开

with open("作业基础版.py","rb") as source_f,open("作业副本.py","wb") as dst_f:
     data = source_f.read()
     dst_f.write(data)

5.with 嵌套语法

with open("作业基础版.py","rb") as source_f:
     with open("作业副本.py","wb") as dst_f:
         data = source_f.read()
         dst_f.write(data)

6.with 的嵌套时 注意:不要对同一个文件进行操作

with open("log.txt","rb") as source_f:
     with open("log.txt","wb") as dst_f:
         data = source_f.read()
         dst_f.write(data)

7.让用户指定要复制的文件

source_path = input("请输入源文件路径:").strip()
dst_path = input("请输入目标文件路径:").strip()

 with open(source_path,"rb") as source_f:
     with open(dst_path,"wb") as dst_f:
         data = source_f.read()
         dst_f.write(data)

基于CMD的复制工具 要达到的效果在CMD中直接输入要复制的文件路径以及 目标文件路径 一回车就完成复制

 1.需要获取CMD输入的参数
import sys # 有一个文件叫sys import是导入这个文件
 sys文件里有一个变量名称叫argv
print(sys.argv) # 得到的就是执行解释器时传入的参数,第一个参数默认就是当前执行文件
 源文件路径
source_path = sys.argv[1]
 目标文件路径
dst_path = sys.argv[2]

with open(source_path,"rb") as source_f:
    with open(dst_path,"wb") as dst_f:
        data = source_f.read()
        dst_f.write(data)

f = open("userdb.txt","at",encoding="utf-8")
for i in range(10):
     data = input(">>:").strip()
     f.write(data)
     print("写了一次")
     f.flush() # 立即将数据写入硬盘,可以保证数据不丢失,但是效率会降低
f.close()

print(f.closed) # 文件是否已经关闭
print(f.encoding) # 获取文件的编码方式

 

文件的修改:

 1.读取文件数据到内存
2.进行修改
3.将修改后的数据写回文件中
new_data = ""
with open("userdb.txt",encoding="utf-8") as f:
    data = f.read()
    datas = data.split("\n")
    for line in datas:
        print(line.split("|")[0])
        name = line.split("|")[0]
        if name == "admin": # 取出名字判断是否等于admin
            name = name+"[is good man]" # 如果是则添加 is good man
            # 取出密码 和手机号 再次拼接为原来的样式
            pwd = line.split("|")[1]
            phone = line.split("|")[2]
            new_line = "|".join([name,pwd,phone])
            new_line += "\n"
            # 拼接修改过的数据
            new_data += new_line
        else:
            # 拼接未被修改的数据
            line += "\n"
            new_data += line

print(new_data)
with open("userdb.txt",mode="wt",encoding="utf-8") as f:
    f.write(new_data)

 以上代码存在什么问题相当于把整个文件数据都存到内存中 会造成内存溢出

文件修改的两方式:

读取一行 修改一行 修改完立马写入硬盘,避免了内存溢出的问题

具体使用哪种方式 的看文件大小
较小的文件 推荐一次性读到内存进行修改 减少io操作
较大的文件 则必须采用第二种方式

with open("userdb.txt",mode="rt",encoding="utf-8") as source_f,open("temp.swap",mode="wt",encoding="utf-8") as dst_f:
    for line in source_f:
        new_line = line.replace("admin","ADMIN")
        dst_f.write(new_line)

import os
os.remove("userdb.txt")  # 删除源文件
os.rename("temp.swap","userdb.txt") # 将交换文件重命名为源文件名

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值