• 包、相对导入和绝对导入、random模块、解压缩


    . 包,也是一种模块
    函数多了,可以分模块文件去管理
    模块多了,可以将模块分类,放在一个个文件夹中,这些文件夹就是包
    为的是使组织机构更加合理清晰

    模块本来就是拿来用的,而包是一些模块的集合,因此它也是被调用的

    文件:
    1.被别人使用
    2.当作脚本自己使用
    执行文件运行时,会将执行文件当前目录加载到sys.path列表中

    import sys
    print(666)
    print(sys.path)
    
    # 666
    # ['C:\Users\Shawn_Huang\Desktop\ATM'
    # 'C:\Users\Shawn_Huang\Desktop\ATM',
    # 'D:\Python36\python36.zip', 'D:\Python36\DLLs',
    # 'D:\Python36\lib', 'D:\Python36', 'D:\Python36\lib\site-packages',
    # 'E:\PyCharm 2018.3.1\helpers\pycharm_matplotlib_backend']
    # 这里列表中的第一个元素就是执行文件当前目录
    
    

    回顾,执行一个模块会发生三件事:

    1.在内存中创建一个以模块名命名的临时名称空间
    2.执行模块代码,将模块里面的代码加载到以模块名命名的临时名称空间
    3.调用模块内的名字必须通过模块名. 的方式调用

    因为包也是模块,是模块的集合体,因此import 一个包名,也会发生三件事:
    1.内存中创建一个以包名命名的名称空间
    2.执行包中的 __init__ 文件,将 __init__ 里面的代码块加载到以包名命名的名称空间
    3.调用包内的名字必须通过包名. 的方式调用
    # 假设有一个包,名为aaa,则在包aaa的 __init__ 文件中创建一个变量x,并给它赋值
    # 在本文件中,可以这样调用:
    # 这里能直接引用aaa,是因为本文件与 aaa 这个包在同一个目录下
    
    import aaa  # 执行 __init__ 文件里的内容
    print(aaa.x)
    
    # 如果 aaa 包里又有另一个 m2.py 文件,怎么办?
    import sys
    print(sys.path)
    # ['C:\Users\Shawn_Huang\Desktop\ATM',
    # 'C:\Users\Shawn_Huang\Desktop\ATM',
    # 'D:\Python36\python36.zip', 'D:\Python36\DLLs',
    # 'D:\Python36\lib', 'D:\Python36', 'D:\Python36\lib\site-packages',
    # 'E:\PyCharm 2018.3.1\helpers\pycharm_matplotlib_backend']
    
    # 这里 aaa 在这个 path 里面,但是 aaa 里面的 m2 不在这个 path 里
    # 因此在 __init__ 里面添加:
    
    from aaa import m2
    
    # 这样的话就可以在本文件里这样:
    import aaa
    print(aaa.m2)  # 这样就会引用 m2 文件里的所有内容
    # <module 'aaa.m2' from 'C:\Users\Shawn_Huang\Desktop\ATM\aaa\m2.py'>
    print(aaa.m2.s1)  # 这里可以被调用
    # 如果 aaa 包里还有很多文件,要想调用它,则可以在 __init__ 里面这样写
    # from aaa import *
    import aaa
    # 如果 aaa 包里还有一个 bbb 包,为了在本文件引用它
    # 应该在 __init__ 文件里加:
    from aaa import bbb
    
    # 引用 包 bbb 里的 __init__ 文件的 s2 变量,可以这样:
    print(aaa.bbb.s2)  # 包bbb的 __init__ 文件内容在这里
    
    # 如果包 bbb 里面又有一个m3.py文件,要引用这个文件的内容,按照以下步骤:
    # 1.在本文件 import aaa
    # 2.在 aaa 包的 __init__ 文件这样写: from aaa import bbb
    # 3.在 bbb 包的 __init__ 文件这样写: from aaa.bbb import m3
    print(aaa.bbb.m3.s3)  # 包 bbb 内的 m3 文件内容在这里
    
    # 上面三步只是为了了解过程,真正程序中可以这样写:—— 直接在本文件中写
    from aaa.bbb import m3
    print(m3.s3)  # 包 bbb 内的 m3 文件内容在这里
    
    # 一定要记住:本文件是执行文件,因此在 sys.path 里面会把它所在的目录添加进去
    # 而 aaa 这个包跟本文件在同一个文件夹内,即同一个目录,因此可以直接引用 aaa 的 __init__ 文件
    
    # 总结
    # 1. from a.b import c  .的左边一定是个包,import后面一定有个具体的名字
    # 2. 包里面的 __init__ 文件想要引用模块必须是from...import...  只有在执行文件里直接写 import,而包是被引用的,不能直接 import
    # 3.from a.b.c.d import e.f.g 错误,import 后面必须只有一个,应该把 .f.g 去掉后才行
    # 相对导入,绝对导入
    # 假设与本文件同目录有个nb.py,内容是这样:
    
    def f1():
        print("111")
    
    def f2():
        print("222")
    
    def f3():
        print("333")
    
    # 在本文件是这样引用的:
    import nb
    
    # 但是,如果随着代码更新,nb模块又增加了一百个函数,放在一个文件肯定不行,要分文件
    # 这时要注意,假如分文件时不能改变调用这个模块的调用方式
    # 这时py文件就应该改为一个包,然后在这个包里创建比如 m1, m2, m3文件,里面放内容
    # 如果只能以下这样调用,怎么改?
    import nb
    nb.f1()  # 111
    nb.f2()  # 222
    nb.f3()  # 333
    nb.f4()  # 444
    nb.f5()  # 555
    nb.f6()  # 666
    
    # 在nb 的 __init__ 里面这样写:—— 这是绝对导入
    from nb.m1 import f1, f2
    from nb.m2 import f3, f4
    from nb.m3 import f5, f6
    
    
    # 但是如果 nb 这里包必须改名,可以直接把 nb 包复制一份,包名重命名为 NB1,
    # 然后在 NB1 的 __init__ 文件里这样写:—— 相对导入
    from .m1 import f1, f2
    from .m2 import f3, f4
    from .m3 import f5, f6
    绝对导入与相对导入总结

    绝对导入: 以执行文件的sys.path为起始点开始导入,称之为绝对导入
    优点: 执行文件与被导入的模块中都可以使用
    缺点: 所有导入都是以sys.path为起始点,导入麻烦

    相对导入: 参照当前所在文件的文件夹为起始开始查找,称之为相对导入符号:
    .代表当前所在文件的文件夹
    ..代表上一级文件夹
    ...代表上一级的上一级文件夹
    优点: 导入更加简单
    缺点: 只能在导入包中的模块时才能使用


    # 二. random 模块 随机模块
    
    import random
    
    print(random.random()) 
    # 大于0小于1之间的随机一个小数
    
    print(random.uniform(1, 3))  
    # 1-3之间的所有小数中的随机一个
    
    print(random.randint(1, 5))  
    # 1-5之间的整数,包括1和5
    
    print(random.randrange(1, 10, 2))  
    # 10以内的奇数的随机一个
    
    print(random.choice(["alex", "wusir", "日天"]))  
    # 多选一, choice()里面必须是容器类数据类型
    
    print(random.sample(["alex", "wusir", "日天", "太白"], 2))  
    # 多选多
    
    l1 = [1, 2, 3, 4, 5]
    random.shuffle(l1)
    print(l1)  # 对原列表打乱顺序
    # 生成随机验证码
    # 5个字符(包含0-9的数字,a-z的小写字母)
    # 思路:验证码肯定是字符串形式
    # 0-9 random.randrange(10)
    # a-z 利用小写字母对应的ascii来写 [chr[i] for i in range(97, 123)]
    # 二选一个字符
    # print(random.randrange(10))
    # print([chr(i) for i in range(97, 123)])
    
    def get_code():
        code = ""
        for i in range(5):
            num = str(random.randrange(10))
            s = chr(random.randint(97, 122))
            # 下面加个大写字母
            s1 = chr(random.randint(65, 90))
            single_s = random.choice([num, s, s1])
            code += single_s
        return code
    
    print(get_code())
    # shutil模块
    # 高级的 文件、文件夹、压缩包 处理模块
    
    # shutil.copyfileobj(fsrc, fdst[, length])
    # 将文件内容拷贝到另一个文件中:
    
    import shutil
    
    shutil.copyfileobj(open('old.xml','r'), open('new.xml', 'w'))
    
    
    # shutil.copyfile(src, dst)
    # 拷贝文件
    shutil.copyfile('f1.log', 'f2.log') #目标文件无需存在
    
    # shutil.copymode(src, dst)
    # 仅拷贝权限。内容、组、用户均不变
    shutil.copymode('f1.log', 'f2.log') #目标文件必须存在
    
    # shutil.ignore_patterns(*patterns)
    shutil.copytree(src, dst, symlinks=False, ignore=None)
    # 递归的去拷贝文件夹
    
    # import shutil
    
    shutil.copytree('folder1', 'folder2',
                    ignore=shutil.ignore_patterns('*.pyc', 'tmp*'))
    
    #目标目录不能存在,注意对folder2目录父级目录要有可写权限,ignore的意思是排除
    # 打包与压缩
    
    import shutil
    import time
    import tarfile
    
    # 同一个文件夹下,直接写 "NB1_bak%s", 不在同一个文件夹写清路径
    # 然后如果压缩至同一个文件夹下,"gztar" 后面不用写 root_dir="路径",反之则反
    shutil.make_archive("NB1_bak%s" % time.strftime("%Y-%m-%d"), "gztar",)
    
    # 解压
    t = tarfile.open("NB1_bak2019-01-10.tar.gz", "r")
    t.extractall("这是新创的文件夹名字")
    t.close()
  • 相关阅读:
    您认为做好测试用例设计工作的关键是什么?
    系统测试的策略
    在C/C++中static有什么用途?
    BUG管理工具的跟踪过程
    详细的描述一个测试活动完整的过程。
    输出一个整数的每一位,如:123的每一位是1 , 2 , 3
    编写代码模拟三次密码输入的场景。 最多能输入三次密码,密码正确,提示“登录成功”,密码错误, 可以重新输 入,最多输入三次。三次均错,则提示退出程序
    获取一个数二进制序列中所有的偶数位和奇数位, 分别输出二进制序列
    求一个整数,在内存当中存储时,二进制1的个数。
    求两个正整数的最大公约数
  • 原文地址:https://www.cnblogs.com/shawnhuang/p/10249945.html
Copyright © 2020-2023  润新知