• 字符编码、文件处理基本操作、函数 04


    一、字符编码

    # 储备知识:
    # 运行python程序的三个阶段:python3 D:	est.py
    # 1、先启动python解释器
    # 2、python3解释器会将test.py的内容当成普通的文本内容读入内存
    # 3、python3解释器开始解释执行刚刚读入内存的内容,开始识别python语法
    # x = "上"
    # print("hello")
    
    """
    1、什么是字符编码
        字符==========编码===============》数字
        字符《==========解码===============》数字
    
    2、哪些地方用到字符编码
        2.1 写程序:
            字符--------编码-------》数字
            字符编码必须包含我们输入的字符与数字的对应关系
            否则,数据在存的时候就出问题了  ......
    
        2.2 执行程序:
            1、前两个阶段
            2、第三个阶段
    
            不乱码的核心:存的时候用什么编码格式,读就应该用什么编码格式
    
    
    
    3、字符编码表
    
        ASCII:只能识别英文字符
            用8bit的二进制数对应一个英文字符
    
            8bit=1Byte
            1024Byte=1KB
            1024KB=1MB
            1024MB=1GB
    
    
            英文字符------------ASCII二进制(内存)------>ASCII二进制(硬盘)
    
    
        GBK:中文、英文字符
            用16bit的二进制数对应一个中文字符
    
            英文、中文字符------------gbk二进制(内存)------>gbk二进制(硬盘)
    
    
        Shift-JIS:日本、英文字符
        Euc-KR:韩文、英文字符
    
    
        unicode:万国字符
            用16bit对应一个字符
    
            万国字符----------------unicode二进制(内存)------>
    
    
    
        utf-8:
            1Byte对应一个英文字符
            3Bytes对应一个中文字符
    
    4、编码与解码
        中文、英文字符------------unicode二进制(内存)------>gbk二进制(硬盘)
        日文、英文字符------------unicode二进制(内存)------>shif-jis二进制(硬盘)
        万国字符------------------unicode二进制(内存)------>utf-8二进制(硬盘)
                        编码                           编码
                        解码                           解码
    
    
    5、结论:
        结论1:
            存不乱=》建议用utf-8格式存入硬盘
            取不乱=》在存不乱的前提下,采用与当成存数据时一样的编码格式
    
        结论2:
            保证py程序前两个阶段不乱码:加文件头#coding:文件的当初存的编码
    
        结论3:
            保证py程序第三个阶段不乱吗:u"字符串"
    """
    
    
    x = ''
    
    
    # 1.1 编码
    # 语法之类型:str------------>bytes
    # 内存角度:  unicode-------->gbk
    # res=x.encode('gbk')
    # print(res,type(res))
    
    
    # 1.2 解码
    # 语法之类型:str<------------bytes
    # 内存角度:  unicode<--------gbk
    # res=x.encode('gbk')
    # print(res)
    
    # xxx=res.decode('gbk')
    # print(xxx,type(xxx))

    二、文件处理基本操作

    #1、操作文件的三个步骤
    
    f=open('a.txt',mode='rt',encoding='utf-8')
    data=f.read()
    print(data)
    # print(type(data))
    # f.close()
    
    # print(f)
    # f.read()
    
    # 2、上下文管理
    # with open('a.txt',mode='rt',encoding='utf-8') as f,
    #         open('b.txt',mode='rt',encoding='utf-8') as f1:
    #
    #     pass

    三、文件的打开模式

    # 文件的打开模式
    # 一:控制文件读写操作的模式
    # 1.1 r(默认):只读,文件不存在则报错,文件存在文件指针会跳到文件开头
    # with open('a.txt',mode='rt',encoding='utf-8') as f:
        # data=f.read()
        # print(data)
        # print(f.readable())
        # print(f.writable())
    
    # 1.2 w:只写,文件不存在则创建一个空文档,文件存在时则清空,文件指针跳到文件开头
    # with open('d.txt',mode='wt',encoding='utf-8') as f:
    #     f.write("你好
    哈哈哈")
    #     f.write("hello")
    #     f.write("我擦了")
    
    # 1.3 a:只追加写,文件不存在则创建一个空文档,文件存在时不清空,文件指针跳到文件末尾
    # with open('d.txt',mode='at',encoding='utf-8') as f:
        # f.write('aaaa
    ')
    
    # 小结:
    # w与a
    # 相同点:在打开了文件不关闭的情况下,连续的写入,新内容总是跟在老内容之后
    # 不同点:在重新打开文件的情况下,w会清空文件,而a模式会将文件至于文件末尾追加写入新内容
    
    # ps:r+、w+、a+
    
    # 二:控制文件读写内容的模式
    # 1.1 t(默认):文本模式
    #       (1)无论读写都是以str为单位,
    #       (2)只能用于文本文件
    #       (3)必须要指定encoding参数
    # with open('a.txt',mode='rt',encoding='utf-8') as f:
    #     # print(f.read())
    #     for line in f:
    #         print(line)
    
    # 1.1 b:原生格式
    #       (1)无论读写都是以bytes为单位,
    #       (2)能用于所有文件
    #       (3)一定不能指定encoding参数
    # with open('文件处理.png',mode='rb') as f:
    #     data=f.read()
    #     print(data)
    
    # with open('a.txt',mode='rb') as f:
    #     data=f.read()
    #     print(data.decode('utf-8'))
    
    
    # with open('a.txt',mode='wb') as f:
    #     f.write("哈哈哈哈".encode('utf-8'))
    
    
    # 小案例:文件copy程序
    
    src_file=input("源文件路径:").strip()
    dst_file=input("目标文件路径:").strip()
    
    with open(r"%s" %src_file,mode='rb') as f1,
            open(r"%s" %dst_file,mode='wb') as f2:
        # data=f1.read()
        # f2.write(data)
    
        for line in f1:
            f2.write(line)

    四、函数基础

    '''
    1、什么是函数
        具备某一功能的工具----》函数
        事先准备工具的过程====》函数的定义
        遇到应用场景拿来就用==》函数的调用
    
    
    2、为何要有函数
        (1)、程序的组织结构不清晰、可读性差
        (2)、代码冗余
        (3)、程序的可维护性差
    3、如何用函数
        原则:先定义,后调用
    
        定义函数的语法:
            def 函数名(参数1,参数2,参数3,...):
                """文档注释"""
                代码1
                代码2
                代码3
                ...
                return 返回值
    
        调用函数
            函数名(值1,值2,值3,...)
    
    '''
    # 一:先定义
    # def func(n,msg):  # func=函数的内存地址
    #     print('-'*n)
    #     print(msg)
    #     print('-'*n)
    
    
    # 二:后调用
    # func(10,'hello')
    # func(5,'world')
    
    
    # 三:
    # 定义阶段:只检测语法,不执行代码
    # def func():
    #     xxx
    
    
    # 调用阶段:根据函数名找到函数的内存地址,然后配合()触发函数体代码的运行
    # func()
    
    # 示例1
    # def bar():
    #     print('from bar')
    #
    # def foo():
    #     print('from foo')
    #     bar()
    #
    # foo()
    
    # 示例2
    # def foo():
    #     print('from foo')
    #     bar()
    #
    # def bar():
    #     print('from bar')
    #
    # foo()
    
    # 四:定义函数的三种形式
    #(1):无参函数
    # def login():
    #     name= input('username>>>: ').strip()
    #     pwd = input('username>>>: ').strip()
    #     if name == 'egon' and pwd == "123":
    #         print('login successful')
    #     else:
    #         print('username or password error')
    #
    # login()
    
    #(2):有参函数
    # def max2(x,y):
    #     # x = 10
    #     # y = 20
    #     if x > y:
    #         print(x)
    #     else:
    #         print(y)
    #
    # max2(10,20)
    # max2(111,222)
    
    #(3):空函数
    # def func():
    #     pass
    
    
    # 五:调用函数的三种形式
    # (1) 语句形式
    # input("please input your name: ")
    
    # def max2(x,y):
    #     # x = 10
    #     # y = 20
    #     if x > y:
    #         print(x)
    #     else:
    #         print(y)
    #
    # max2(11,22)
    
    
    # (2) 表达形式
    # name = input("please input your name: ")
    
    # def max2(x,y):
    #     if x > y:
    #         return x
    #     else:
    #         return y
    #
    # res=max2(111,222) * 12
    
    
    
    
    # (3) 当作参数传给另外一个函数
    def max2(x,y):
        if x > y:
            return x
        else:
            return y
    
    # print(max2(111,222))
    
    # print(max2(max2(111,222),333))
    
    # 六:函数返回值return
    # (1) return是函数结束的标志,函数内可以有多个return,但只要执行一次整个函数就会立即终止,并且会将return后的结果当作本次调用的返回值返回
    # def func():
    #     print('hello1')
    #     return 111
    #     print('hello2')
    #     return 222
    #     print('hello3')
    #     return 333
    #
    # func()
    # (2) return可以返回的值的个数
    #   return 值:返回一个值
    #   return 值1,值2,值3: 把多个值放到一个元组内返回
    # def func():
    #     return 1,33.3,[1,2,3]
    
    # res=func()
    # print(res)
    
    #  没有return或者就一个单独的return:默认返回的是None
    # def func():
    #     pass
    #
    # res=func()
    # print(res)

    五、函数参数

    # 一: 函数的参数分为形参与实参
    # (1) 形参: 在函数定义阶段,括号内定义的参数(变量名),称之为形式参数,简称形参
    # def func(x,y):
    #     print(x,y)
    # (2) 实参: 在函数调用阶段,括号内传入的值(变量值),称之为实际参数,简称实参
    # func(1,2)
    
    # 二: 详细介绍形参与实参
    # 1 位置参数
    # (1) 位置形参:在函数定义阶段,按照从左到右的顺序依次定义的形参
    #       特点: 必须被传值
    # def func(x,y):
    #     print(x,y)
    
    # (2) 位置实参:在函数调用阶段,按照从左到右的顺序依次传入的值
    #       特点:按照位置与形参一一对应
    # func(1,2)
    # func(1,2,3)
    # func(1,)
    
    # func(1,2,3,4,5,)
    
    # 2 关键字实参: 在函数调用阶段,按照key=value的形式传值
    #       特点: 可以打破传值的顺序,但仍能指名道姓地为形参赋值
    # func(y=2,x=1)
    
    #       注意:可以混用位置实参与关键字实参,但是
    #              (1)位置实参必须放在前面
    #              (2)不能为同一个形参重复赋值
    # func(111,y=2)
    # func(y=2,111)
    # func(111,x=222,y=333)
    
    # 3 默认形参: 在函数定义阶段,就已经为形参赋值,该形参称之为默认形参
    #       特点: 调用时可以不用为默认形参传值
    # def func(x,y=222):
    #     print(x,y)
    
    # func(111)
    # func(111,333)
    
    #       注意:可以混用位置形参与默认形参,但是
    #           (1) 位置形参必须放在前面
    #           (2) 默认形参的值只在函数定义阶段赋值一次,拿到的一个内存地址
    #               为函数的每次调用都是独立,默认形参的值通常应该是不可变
    # def func(y=222,x):
    #     print(x,y)
    
    # m = 222
    # m = []
    #
    # def func(x,y=m):
    #     print(x)
    #     print(y)
    
    # m = 333
    # m.append(44444444444)
    # func(111)
    
    
    # def func(name,hobby,hobbies=None):
    #     # name="egon"
    #     # hobby="music"
    #     if hobbies is None:
    #         hobbies = []
    #     hobbies.append(hobby)
    #     print('%s 的爱好是 %s' %(name,hobbies))
    #
    # func('egon','music')
    #
    # func('lili','read')
    #
    # func('jack','movie')
    
    
    # 案例:
    # def register(name,age,sex='male'):
    #     print(name,age,sex)
    #
    # register("egon",18)
    # register("jack",19)
    # register("tom",20)
    # register("lili",21,'female')
    
    
    # 4 *与**在形参与实参的应用
    # 可变长的实参指的是在调用函数时括号内传入的实参值的个数不固定
    # 而实参无非两种格式:位置实参关键字实参
    # 对应着必须有专门的形参来接收溢出位置实参与关键字实参
    
    # 4.1 *与**在形参中的应用
    # (1) *在形参中: *会把溢出的位置实参存成元组的形式,然后赋值给其后的形参名
    # def func(x,*args): # x=1,args=(2,3)
    #     print(x,args)
    #
    # func(1,2,3)
    
    
    # (2) **在形参中: **会把溢出的关键字实参存成字典的形式,然后赋值给其后的形参名
    # def func(x,**kwargs): # x=1,kwargs={"c":3,"a":1,"b":2}
    #     print(x,kwargs)
    
    # func(x=1,a=1,b=2,c=3)
    
    # 4.2 *与**在实参中的应用
    # def func(x,y,z):
    #     print(x,y,z)
    
    # (1) *在实参中:*会将实参值打散成位置实参
    # func(*[1,2,3])  # func(1,2,3)
    
    # (2) **在实参中:**会将字典格式的实参值打算成关键字实参
    # func(**{"a":1,'b':2,'c':3})  # func(a=1,b=2,c=3)
    # func(**{"x":1,'y':2,'z':3})  # func(x=1,z=3,y=2)
    
    # func(*"hello")  #
    # func(*{"aaa":1,'bbb':2,'ccc':3})  # func('aaa','bbb','ccc')
    
    
    # 4.3 可以混用: **必须在*的后面
    # def wrapper(*args,**kwargs):  # args=(1,2,3,4,5)  kwargs={"a":1,'b':2,'c':3}
    #     print(args)
    #     print(kwargs)
    
    # wrapper(1,2,3,4,5,a=1,b=2,c=3)
    
    
    # def wrapper(*args,**kwargs):  # args=("h","e")  kwargs={"a":1,'b':2,'m':333,'n':4444}
    #     print(args)
    #     print(kwargs)
    #
    # wrapper(*'he',a=1,b=2,**{'m':333,'n':4444})  # wrapper("h","e",a=1,b=2,n=4444,m=333)
    
    
    
    # 非常重要的一种格式
    # def index(x,y):
    #     print('index===>',x,y)
    #
    # def wrapper(*args,**kwargs):  # args=(1,2,3)  kwargs={"a":1,'b':2,'c':3}
    #     index(*args,**kwargs)  # index(*(1,2,3).**{"a":1,'b':2,'c':3})
    #                           #  index(1,2,3,a=1,b=2,c=3)
    #
    #     # index(1,y=2)
    #
    # wrapper(1,y=2)

    六、文件的修改

    # 验证:文件修改的本质都是用新内容覆盖老内容
    # with open('aaa.txt',mode='r+t',encoding='utf-8') as f:
    #     f.write("李四")
    
    # 修改文件的方式一
    # 思路:
    # (1)先将硬盘中文件的内容一次性全部读入内存
    # (2)在内存中修改完毕后,再覆盖写原文件
    
    # 优点:不需要额外占用硬盘空间
    # 缺点:会过多占用内存空间
    
    
    # with open('bbb.txt', mode='rt', encoding='utf-8') as f1:
    #     data = f1.read()
    #     res = data.replace('lqz', 'dsb')
    #
    # with open('bbb.txt', mode='wt', encoding='utf-8') as f2:
    #     f2.write(res)
    
    # 修改文件的方式二
    # 思路:
    # (1)以读模式打开源文件,然后写模式打开一个临时文件
    # (2)从源文件中读出一行内容,修改完毕后,写入临时文件
    # (3)循环往复,知道源文件内容都读完,删除源文件,将临时文件重命名为源文件名
    
    
    
    # 优点:节省内存
    # 缺点:需要额外占用硬盘空间
    
    import os
    
    with open('bbb.txt', mode='rt', encoding='utf-8') as f1,open('.bbb.txt.swp', mode='wt', encoding='utf-8') as f2:
        for line in f1:
            f2.write(line.replace('dsb','lqz'))
    
    os.remove('bbb.txt')
    os.rename('.bbb.txt.swp','bbb.txt')
  • 相关阅读:
    0x55 环形与后效性问题
    0x54 树形DP
    0x53 区间DP
    0x52 背包
    0x51 线性DP
    poj1015 Jury Compromise
    973、863计划取消 国家重点研发计划启动
    中科院院士陈仙辉回母校:英雄不问出处 成功要靠努力和实力来实现
    Resume (Curriculum Vitae)
    阅读linux内核代码的工具-- Source Insight
  • 原文地址:https://www.cnblogs.com/2722127842qq-123/p/13448799.html
Copyright © 2020-2023  润新知