python基础学习笔记

摘要:

  此博文是初步探索python世界的经历,主要是归纳总结python的基础和特性,过程是一边观看视频一边敲代码学习并记录下笔记,文字较少,主要以代码为主通过注释标注重点,有需要步入python编程的,可参考此学习途径。

开发环境:python3.11.0,vscode

关键词学习笔记python零基础小甲鱼鱼C论坛学习途径

声明:本文作者原创,转载请附上文章出处与本文链接。

正文:

视频:

  B站小甲鱼python教学基础扎实,也有不少拓展的知识点,零基础学习python够用,主要要跟着多敲代码,多整理笔记。鱼C论坛也有对应的python板块,每章有课后作业等,有需要可去观看解答,不一定需要,能跟着视频敲出代码运行起效果就好。

在这里插入图片描述

跳转链接点这里~~

学习随笔

  P1~P19主要是介绍,环境搭建以及一些基础中的基础,有一定其它语言的学习这些都非常容易入门,所以笔记记录的主要是P20之后的内容,代码都可直接运行,内容是自己的理解,想到哪里记哪里,单看云里雾里,得结合视频,随意参考即可,按自己节奏走。P20之后的内容代码采用了分支处理,只要改变一个变量即可选择不同P章节运行。

P1~P19:变量和分支循环

练手敲的代码

import decimal

x = 1 + 2j
x.real
x.imag
divmod(-3, 2)   # 地板除, 取余

if True and False or False and not True:    # 短路逻辑、优先级 not > and > or
    print("fuck")

num = 123
match num:
    case 1:
        print("1")
    case 2:
        print("2")
    case _:
        print("not", end=" ")
# """ 这才是注释符号阿 """
import random
import decimal

num, count = random.randint(0, 10), 8
print("answer:" + str(num) + "\n")

while count:
    temp = input("How much num?")
    guess = int(temp)
    if num == guess:
        print("YES")
        break
    else:
        if guess > num:
            print("NO, so big")
        elif guess < num:
            print("NO, so small")
    count -= 1
    print(count)

print("END")


P20~P27:列表list,元组tuple
# 列表和地址很像

inis = 1# inis为控制运行分支变量,改变inis的值变更运行不同P,后续类同

# 列表1
if inis == 1:
    real = [1, 2, 23, 4, "dasdq"]
    # for each in real:
    #     print(each)

    real[-1]
    real[0:3]
    real[:3]
    real[3:]
    real[:]
    real[::2]
    real[::-2]
    real[::-1]
    # print(real[1:3])

# 列表2
elif inis == 2:
    real = [1, 2, 23, 4, "dasdq"]
    real.append(123)                        # hulei
    real.extend(["wdfk", 1.134, False])     # hulei

    real[len(real):] = ["dnm"]
    real[len(real):] = [88, 3.14, "wqnmd"]

    real.insert(2, [123, 321])
    real.remove("dnm")
    print(real)
    real.remove(23)
    print(real)
    real.clear()

# 列表3
elif inis == 3:
    num = [1, 2, 3, 89, 64, 13, 57, 91, 32, 5]
    num.sort()
    num.reverse()
    num.sort(reverse=True)
    num.count(13)
    num.index(91)
    num1 = num.copy()
    num1 = num[:]

# 列表4
elif inis == 4:
    list = [1, 2, 3]
    list2 = [4, 5, 6]
    list + list2
    list * 3        # 列表地址的拷贝,不是新建

    matrix = [[1, 2, 3],
              [4, 5, 6],
              [7, 8, 9]]

    A = [0] * 3
    for i in range(len(A)):
        A[i] = [0] * 3
    print(A)
    B = [[0] * 3] * 3   # 结果相同原理不同

# 列表5
elif inis == 5:
    import copy
    x = [1, 2, 3]
    y = x.copy
    y = x[:]    # 一样,浅拷贝,对嵌套列表(二维数组)不行,

    x = [[1, 2, 3],
         [4, 5, 6],
         [7, 8, 9]]
    y = copy.deepcopy(x)    # 深拷贝

# 列表6
elif inis == 6:
    # 列表推导式    更快,C语言实现的
    x = [i for i in range(10)]
    # print(x)
    x = [i * 2 for i in range(10)]
    # print(x)
    code = [ord(i) for i in "wdnmlgb"]
    # print(code)

    matrix = [[1, 2, 3],
              [4, 5, 6],
              [7, 8, 9]]
    col2 = [row[1] for row in matrix]   # row == ,matrix[?]
    # print(col2)
    col2 = [matrix[i][i] for i in range(len(matrix))]   # len(matrix) == 3
    print(col2)
    col2 = [matrix[i][-i+2] for i in range(len(matrix))]   # len(matrix) == 3
    print(col2)

# 列表7
elif inis == 7:
    s = [[0] * 3 for i in range(3)]
    print(s)

    words = ["Great", "Fishc", "Brilliant", "Excellent", "Fantistic"]
    words = [i for i in words if i[0] == 'F']
    print(words)

    # 嵌套列表推导式
    matrix = [[1, 2, 3],
              [4, 5, 6],
              [7, 8, 9]]
    flatten = [col for row in matrix for col in row]
    print(flatten)

    _ = [[x, y] for x in range(10) if x % 2 == 0
                for y in range(10) if y % 3 == 0]
    print(_)

# 元组不可变,可读不可写    ;   除了跟修改相关的操作不行,和没有元组推导式。其它操作和列表类似 
elif inis == 8:
    rhyme = (1, 23, 7, 13, 9, 123, 10, "wdnmd")

    t = (1, 22, "wdfuck")
    x, y, z = t

    x, y, *z = "wdfuck"
    # print(z)

    x = [1, 2, 3]
    y = [4, 5, 6]
    _ = (x, y)      # 存放列表(索引/地址)就可更改
    print(_)
    x[1] = 9
    print(_)

P28~P33:字符串string
inis = 6
# 字符串1
if inis == 1:
    x = "123321"    # 回文数
    print("yes") if x == x[::-1] else print("no")

    print(type(x))

    # 字符串处理函数合集:https://fishc.com.cn/thread-183975-1-3.html

# 字符串2
elif inis == 2:
    print("a lot of funcation")

# 字符串3
elif inis == 3:
    import keyword
    keyword.iskeyword("for")

# 字符串4
elif inis == 4:
    str = ".".join(["www", "wdfk", "com"])
    print(str)
    str = "".join(["wdfk", "wdfk"])     # 大数据效率高
    print(str)
    str = "wdfk"
    str += str                          # 小数据差不多
    print(str)

# 字符串5
elif inis == 5:
    num = 250
    str = "wdfk num:{}".format(num)
    print(str)

    str = "{1}wdfk,{0}250".format("wdfk", 250)
    print(str)

    str = "{num}wdfk,{wdfk}250".format(wdfk="wdfk", num=250)
    print(str)

    # 填充空格、其它字符;数字补齐0感知正负号

# 字符串6
elif inis == 6:
    # 正负号{:+}/{:-}、千位符{:,}、限制位({:2f}/{:2g} {:.2})
    # 类型{:(type)}
    "{:b}".format(80)
    "{:e}".format(3.1415)
    "{:.2%}".format(0.88)

    # f-string  format版“语法糖”    性能略胜一筹:V3.6
    str = f"wdfk {250}"
    print(str)

P34~P41:序列sequence,字典dict,集合set
inis = 8

# 序列上
if inis == 1:
    # 列表、元组、字符串都是序列
    "123" + "123"
    "123" * 3

    s = [1, 2, 3]
    id(s)
    t = [1, 2, 3]
    print(s is t)           # false     is not

    print("wdfk" in "wdfk 250")    # true   in not

    del s, t
    x = [1, 2, 3, 4, 5]
    del x[::2]
    print(x)

# 序列中
elif inis == 2:
    # --list()变列表、tuple()变元组、str()变字符串
    print(list("wdfk"))

    # min、max、len、sum
    min([1, 2, 3, 4, 5, 6])
    min(1, 2, 3, 4, 5)

    # sorted返回新的列表、reversed返回的是一个迭代器

# 序列下
elif inis == 3:
    x = [1, 2, 0]
    y = [0, 0, 0]
    z = [1, 1, 1]
    all(x)      # false y:false z:true
    any(x)      # true  y:false z:true

    seasons = ["chun", "xia", "qiu", "don"]
    # enumerate(seasons)   # 创建枚举对象
    print(list(enumerate(seasons)))
    print(list(enumerate(seasons, 10)))

    x = [1, 2, 3]
    y = [9, 8, 7]
    z = "wdnmd"
    zipVal = zip(x, y, z)
    print(list(zipVal))
    import itertools
    print(list(itertools.zip_longest(x, y, z)))

    print(list(map(ord, "wdnmd")))
    print(list(map(pow, [2,2,8], [1,8,2]))) # max

    print(list(filter(str.islower, "WdnMD")))

    # 迭代器一定是迭代对象。迭代对象可复用,迭代器是一次性(C++ 的传地址传变量?有点类似)
    x = [1, 2, 3, 4, 6]
    y = iter(x)
    print(type(x), type(y))
    next(y, "NULL")
    next(y, "NULL")
    next(y, "NULL")
    next(y, "NULL")
    next(y, "NULL")
    print(next(y, "木了"))

# 字典上
elif inis == 4:
    # 字典是python中唯一实现映射关系的内置类型
    table = {",":"w", ".":"d", "/":"n", ";":"m", "'":"d"}
    code = input("input:")
    split_code = code.split(" ")

    result = [table[each] for each in split_code]
    print(result)

# 字典中
elif inis == 5:
    table = {",":"w", ".":"d", "/":"n", ";":"m", "'":"d"}
    type(table)
    # 添加、修改
    table["["] = "F"
    # 创建
    table = {",":"w", ".":"d", "/":"n", ";":"m", "'":"d"}
    table = dict(我去你的="w", 神经病="d")
    table = dict(zip([",", ".", "/", ";", "'"], ["w", "d", "n", "m", "d"]))
    # ……

    table = dict.fromkeys("wdfk", 250)  # 创
    print(table)
    table.pop('f', "没找到")            # 删
    table.popitem()
    print(table)
    table.clear()                       # 清

# 字典下
elif inis == 6:
    table = dict.fromkeys("wdfk")
    print(table)
    table.update(w='F', d='U')          # 改
    table.update({'f':250, 'k':438})
    print(table)

    table.get('f', "木有")              # 查
    table.setdefault('h', "wy")

    # 视图对象
    keys= table.keys()
    values = table.values()
    items = table.items()
    # table改变,这三个都会相应改变

    x = table.copy()
    len(table)
    # in、not in、list、iter、reversed、

    # 嵌套
    table = {"w":{"f":1,"u":2,"c":3,"k":4}, "d":{"q":"S","n":"B",200:"俩佰",5:"伍"}} 
    print(table["d"]["q"]) 

    # 字典推导式
    table = {",":"w", ".":"d", "/":"n", ";":"m", "'":"d"}
    a = {v:k for k,v in table.items()}  # 嵌套不行      
    print(a)

    a = {v:k for k,v in table.items() if v == 'w'}    
    print(a)

# 集合上
elif inis == 7:
    # 创    (元素唯一和字典key性质一致)(集合无序)
    setValue = {"wdnmd", "fuck"}
    print(type(setValue))
    print(setValue)
    setValue = set({"wdnmd", "fuck"})
    print("fuck" in setValue)

    len([1,2,2,3,4]) == len(set([1,2,2,3,4]))   # false

    setValue = set("wdnmd")
    print(setValue.isdisjoint (set("fuck")))            # 集合是否 没有交集 (参数为列表等也可)
    print(setValue.issubset("wdnmd,fuck"))              # 集合是否为参数的子集
    # setValue <= set("wdnmd,fuck")
    print(setValue.issuperset("wd"))                    # 集合是否为参数的超集
    # setValue >= set("wd")

    print(setValue.union("fuck"))                       # 组成并集  
    # setValue | set("fuck")
    print(setValue.intersection("fucknmd"))             # 两个相交的交集
    # setValue & set("fucknmd")
    print(setValue.difference("fuck"))                  # 集合不在参数内的元素 差集
    # setValue - set("fuck")
    # 都是可以多参数,下面的对称差集不行 
    print(setValue.symmetric_difference("wdfuck"))   
    # setValue ^ set("wdfuck")

# 集合下
elif inis == 8:
    froset = frozenset("wdnmd")             # 不可变的集合
    setVal = set("wdnmd")
    setVal.update([1, 4], "89")             # 参数添加进集合 (frozenset会异常)(*orthers,有s是多个参数)
    print(setVal)

    # setVal.intersection_update、setVal.difference_update、setVal.symmetric_difference_update 
    # 添加_update后会更改setVal的内容

    setVal.add("45")
    setVal.remove("45")                     # setVal.discard 找不到静默处理
    setVal.clear()

    # 嵌套集合(涉及可哈希性质,hash())  set不行,只能用frozenset
    nestSet = {frozenset([1,2,3]), 8, 10}
    print(nestSet)
    

P42~P53:函数function
inis = 12

# 函数Ⅰ
if inis == 1:
    def func(name, times):
        for i in range(times):
            print(f"fuck {name}")
        return "wdnmd"

    print(func("wdfk",2))


# 函数Ⅱ
elif inis == 2:
    # 关键字参数   (位置参数必须在关键字参数之前)
    def func(s, vt, o):
        print( "".join((o, vt, s)) )

    func(o="fuck", vt="you", s="today")

    # 默认参数  (和C++默认参数一致)

    # 参数限制  /   *
    def funcxie(a, /, b, c):            # / 左侧必须用位置参数,右侧可用关键字参数
        print(a,b,c)
    
    def funcxing(a, *, b, c):           # * 右侧必须用关键字参数,左侧可用位置参数
        print(a,b,c)
    funcxing(1,b=2,c=3)

# 函数Ⅲ
elif inis == 3:
    # 收集参数(多参数)
    def func(*args):                        # args 为元组
        print("{}个".format(len(args)))
        print("最后一个参数{}".format(args[len(args)-1]))
        return 1,2,3                        # 返回多个值也是利用元组打包的性质

    func(1,2.3)

    def funcKey(*args, a, b):
        print(args, a, b)
    funcKey(1, a=2, b=3)

    def funcDict(**dict):                   # dict字典  *限制右边必须为关键字参数
        print(dict)

    funcDict(a=1, b=2, c=3)

    # 混合
    def funcBlend(a, *b, **c):
        print(a,b,c)

    funcBlend(1,2,3,4,5,q=6,w=7,e=8)

    # 解包参数
    args = (1,2,3,4)
    def funcUnpack(a,b,c,d):
        print(a,b,c,d)

    funcUnpack(*args)

    args = dict(a=10,b=9,c=8,d=7)
    funcUnpack(**args)

# 函数Ⅳ
elif inis == 4:
    # 作用域    和C++类似   有global函数可以在函数内修改全局变量
    # 嵌套函数
    def funcA():
        x = "wdnmd"
        def funcB():
            x = "fuck"
            print("funcB:", x)
        funcB()
        print("funcA:", x)
    
    funcA()
    
    def funcA():
        x = "wdnmd"
        def funcB():
            nonlocal x              # 统一内外函数的变量
            x = "fuck"
            print("funcB:", x)
        funcB()
        print("funcA:", x)
    
    funcA()
    
    # (变量覆盖)LEGB规则:L:Local; E:Enclosed; G:Global; B:Build-In;

# 函数Ⅴ
elif inis == 5:
    # 闭包 工厂 
    def power(exp):
        def exp_of(base):
            return print(base ** exp)
        return exp_of
    square = power(2)
    cube = power(3)
    square(3)       # 3的2次方
    cube(3)         # 3的3次方
    
    # 闭包工厂功能可用作游戏角色的移动

    def funcInit(x = 0, y = 0):
        def innerFunc(type):
            def funcA(xA, yA):
                nonlocal x,y
                x += xA
                y += yA
                print("funcA:",x,y)
            def funcB(xB, yB):
                nonlocal x,y
                x += xB
                y += yB
                print("funcB:",x,y)
            if type == 0:
                return funcA
            elif type == 1:
                return funcB
        return innerFunc            # 或者  return {'func1':funcA, 'func2':funcB}   原理就是让funcA、funcB在同一层

    funcFactory = funcInit()
    func1 = funcFactory(0)
    func2 = funcFactory(1)

    func1(1, 1)
    func2(2, 2)
    func1(3, 3)


# 函数Ⅵ
elif inis == 6:
    # 函数作参数    制作最简单的程序⏲
    import time
    def timer_master(func):
        print("begin")
        start = time.time()
        func()
        stop = time.time()
        print("stop")
        # print(f"time:{(start-stop):.2f}秒")
        print("time:{:.2f}秒".format(stop-start))

    def funcTime():
        time.sleep(2)
        time.sleep(0.05)
        print("funcTime End")
    # timer_master(funcTime)
     
    # 装饰器(原理闭包)    阔以多个装饰器作用一个函数,从近往远依次调用 
    def timer_master(func):
        def call_func():
            print("begin")
            start = time.time()
            func()
            stop = time.time()
            print("stop")
            # print(f"time:{(start-stop):.2f}秒")
            print("time:{:.2f}秒".format(stop-start))
        return call_func
    
    @timer_master           # 语法糖    == (funcTime = timer_master(funcTime))
    def funcTime():
        time.sleep(2)
        time.sleep(0.05)
        print("funcTime End")

    # funcTime()

    # 装饰器传参    多套一次闭包,把参数传进去
    def logger(msg):
        def timer_master(func):
            def call_func():
                print("begin")
                start = time.time()
                func()
                stop = time.time()
                print("stop")
                print("{0}time:{1:.2f}秒".format(msg, stop-start))
            return call_func
        return timer_master
    
    @logger(msg="funcTime")           # == (funcTime = logger(msg="funcTime")(funcTime))
    def funcTime():
        time.sleep(2)
        time.sleep(0.05)
        print("funcTime End")

    funcTime()

# 函数Ⅶ
elif inis == 7:
# lambda (一行流) 最大优势就是阔以出现在def 不允许出现的地方,简单的功能就不需要def
    def squareX(x):
        return x * x
    squareY = lambda y : y*y
    # squareX == squareY

    # 可出现在列表、元组等
    y = [lambda x:x*x, 2, 3]
    print(y[0](y[1]), y[0](y[2]))

    mapped = map(lambda x:ord(x)+10, "wdnmd")
    print(list(mapped))

# 函数Ⅷ
elif inis == 8:
    # 生成器yield,保存调用函数的状态(闭包、全局变量)
    def counter():
        i = 0
        while i <= 5:
            yield i         # 每次调用返回 yield    类似return但没return的阻断,下面语句还可运行,并会保存着
            i += 1

    for i in counter():
        print(i)

    print(next(counter()))  # 生成器也是一种迭代器

    # 生成器表达式  (元组?)  列表表达式是一次性全输出、生成器表达式是一次调用只输出一个
    t = (i ** 2 for i in range(10))
    print(type(t), next(t))
    print(next(t))
    print(next(t))
    

# 函数Ⅸ
elif inis == 9:
    # 递归  和C++一样,了解就好 函数掉用函数
    # 生成器实现斐波那契数列
    def fib(n):
        back1, back2 = 0, 1
        while (n!=-1):
            yield back1
            back1, back2 = back2, back1+back2
            n -= 1
    n = 120
    for val in fib(n):
        if(n == 0):
            print(val)
        n -= 1

# 函数Ⅹ
elif inis == 10:
    # 递归 汉诺塔
    def hanoi(n, x, y, z):
        if(n == 1):
            print(x, "-->" ,z)
        else:
            hanoi(n-1, x, z, y)
            print(x, "-->", z)
            hanoi(n-1, y, x, z)

    n = int(input("层数:"))
    hanoi(n, 'A', 'B', 'C')

# 函数Ⅺ
elif inis == 11:
    # 编写函数文档
    def exchange(dollar, rate = 7.17):
        """
        功能:美元转人民币   
        参数:美元,汇率
        返回:结果
        """
        return dollar * rate
    help(exchange)

    # 类型注释  没有强制作用,只是推荐函数参数类型, 返回的类型
    def  times(s:str, n:int) -> str:
        return s * n
    print(times(5, 5))

    # 内省      __xx__ 都是函数的内省(程序自我检测的机制),内在属性说明等
    print(exchange.__name__)
    print(times.__annotations__)

# 函数Ⅻ
elif inis == 12:
    import functools
    # 高阶函数  函数做函数参数
    # https://fishc.com.cn/thread-209319-1-2.html

    # 偏函数    对指定的函数二次包装,例如包装pow函数的次幂
    square = functools.partial(pow, exp=2)
    print(square(2))
    cube = functools.partial(pow, exp=4)
    print(cube(2))

    # @wraps装饰器,跟闭包,函数内省相关
    def timer_master(func):
        @functools.wraps(func)                              # 注释这一句的话,下面print(funcTime.__name__) 输出 call_func
        def call_func():
            print("begin")
            start = time.time()
            func()
            stop = time.time()
            print("stop")
            # print(f"time:{(start-stop):.2f}秒")
            print("time:{:.2f}秒".format(stop-start))
        return call_func
    
    @timer_master
    def funcTime():
        time.sleep(2)
        time.sleep(0.05)
        print("funcTime End")
    
    print(funcTime.__name__)

P54~P58:永久储存memory,异常abnormal
inis = 5

# 永久存储↑
if inis == 1:
    # 创建打开文件
    file = open("wdnmd.txt", "w")
    file.write("wdnmdlch, fuck")
    file.writelines({"123\n","987\n"})

    file.close()    # 需要关闭刷新缓存,write才有正式写入   or open和close是一对,不可分
    file = open("wdnmd.txt", "r+")
    for each in file:
        print(each)
    print(file.tell())

    file.seek(0)
    print(file.read())
    
    file.write("天王盖地虎, 宝塔镇河妖\n")
    file.flush()    # 刷新缓存

    file.truncate(24)   # 截断

    file = open("wdnmd.txt", "w")           # 也会截断,w打开会删内容    和mode:w有关,r+不会
    file.close()
    
# 永久存储-
elif inis == 2:
    # 路径处理  pathlib 3.4才有
    from pathlib import Path
    print(Path.cwd())
    dirPath = Path("D:\CODE\python")
    txtPath = dirPath / "wdnmd.txt"

    print(dirPath.is_dir())
    print(txtPath.exists())     # 路径是否存在
    print(txtPath.suffix)       # 文件后缀
    # …………

    # 相对路径、绝对路径
    Path("../python").resolve() # 相对路径转绝对路径

    # 看文档https://fishc.com.cn/thread-210695-1-6.html

# 永久存储↓
elif inis == 3:
    # with上下文管理器  确保资源的释放,不需要close
    with open("wdnmd.txt", "w") as f:
        f.write("wdnmd, fuck")

    # 将python对象序列化(转为二进制文件)pickle
    import pickle
    import time

    x, y, z = 7748, 250, 438
    s = "wdnmd"
    a = {1:"s13", 2:"cnmlch", 3:"fuck"}

    with open("./param.pkl", "wb") as f:
        pickle.dump((x,y,z,s,a), f)

    time.sleep(1)

    with open("./param.pkl", "rb") as f:
        q, w, e, r, t = pickle.load(f)

    print(q, w, e, r, t)

# 异常↑
elif inis == 4:
    # 查找异常  https://fishc.com.cn/thread-211613-1-2.html

    # 处理异常  try -except
    try:
        1 / 0
    except:
        print("wdnmd")

    try:
        1
        # 502 + "fuck"                    # 错误类型是   TypeError
    except ZeroDivisionError as e:      # 指定识别异常类型 e:错误原因
        print("e")

    try:
        1 / 0
        502 + "fuck"
    except (ZeroDivisionError, ValueError, TypeError):      # 元组聚合
        pass

    try:
        1 / 0
        502 + "fuck"
    except ZeroDivisionError:           # 分开处理
        pass
    except TypeError:
        pass

# 异常↓
elif inis == 5:
    # try-except-else       无异常运行else  
    # try-except-finally    有无异常都运行finally

    # 嵌套异常
    try:
        try:
            502 + "fuck"
        except:
            print("内部异常")
        1 / 0 
    except:
        print("外部异常")
    finally:
        print("收尾")

    # raise ValueError("自爆")          # 自爆,主动引发异常
    s = "wdnmd"
    assert s != "wdnmd"                 # 条件为false 主动引发异常                 


P59~P72:类和对象class and object(1)
inis = 11

# 类和对象Ⅰ
if inis == 1:
    # 创建类    (封装)
    class People:
        age = 130
        color = "yellow"
        
        def speakOen(self):                     # 类内函数 第一个参数都要设为self,不然会异常
            print("wdnmdlch, fuck")
            return
        def speakTwo(self, val:str="7438,cnmlch"):
            print(val)
            return
    p = People()                                # self  实例对象本身
    print(p.color)
    p.speakTwo("123")

    p.hight = 188
    print(p.hight)                              # 和C++不同,还可以直接加属性,当然只适用当前对象,没影响到类
    
# 类和对象Ⅱ
elif inis == 2:
    # 继承
    class A:
        num = 250
        def func(self):
            print("A:wdnmdlch")
    class B(A):
        num = 7438
    b = B()
    print(b.num)
    b.func()

    print(isinstance(b, B))
    print(isinstance(b, A))     # 对象所属类
    print(issubclass(B, A))     # 类B是否为A的子类

    # 多重继承
    class V:
        num = 38
        def func(self):
            print("V:fuckcnmlch")
    class C(A,V):
        pass
    c = C()
    print(c.num)                # 以继承的顺序(A,V),同名的先继承先确定(A)

    # 组合(类内声明类对象)
    class C:
        a = A()
        v = V()
        def func(self):
            self.a.func()       # (计算机)确定存储位置吧;绑定(码农)
            self.v.func()
    c = C()
    c.func()

# 类和对象Ⅲ
elif inis == 3:
    # self 函数改属性
    class C:
        def setX(self, val):
            self.x = val
    c = C()
    c.setX(250)
    print(c.__dict__)

    # 用空类来当字典dict,好像挺方便的?
    class C:
        pass
    c = C()
    c.x = 250
    c.val = "wdnmlch"
    print(c.x, "\t", c.val)

# 类和对象Ⅳ
elif inis == 4:
    # 构造函数  __init__ 
    class C:
        def __init__(self, x, y, *args, **kwargs) -> None:
            print('C的init被调用')
            self.x = x
            self.y = y
        def add(self):
            return self.x + self.y
    
    c = C(4,8)
    print(c.add())

    #多继承 __init__ 及super初实验
    class A:
        def __init__(self, a, *args, **kwargs) -> None:
            print('A的init被调用')
            self.a = a
        def mul(self):
            return self.a ** 2

    class D(C, A):
        def __init__(self, x, y, a) -> None:
            C.__init__(self, x, y)
            A.__init__(self, a)
            # super().__init__(x,y,a)                     # 这种情况不适用super.__init__    用类名.__init__更适合  
        
        def add(self):
            return C.add(self) + self.a
        
    d = D(1,2,3)
    print(d.add())
    print(d.mul())

# 类和对象Ⅳ super 补充
elif inis == 4.5:
    # super 适用菱形继承
    # mro 继承 在搜索方法时,是按照 __mro__ 的输出结果 从左至右 的顺序查找的
    # 如果在当前类中 找到方法,就直接执行,不再搜索
    # 如果 没有找到,就查找下一个类 中是否有对应的方法,如果找到,就直接执行,不再搜索
    # 如果找到最后一个类,还没有找到方法,程序报错
    class Parent(object):
        def __init__(self, name, *args, **kwargs):  # 为避免多继承报错,使用不定长参数,接受参数
            print('parent的init开始被调用')
            self.name = name
            print('parent的init结束被调用')
 
    class Son1(Parent):
        def __init__(self, name, age, *args, **kwargs):     # 为避免多继承报错,使用不定长参数,接受参数
            print('Son1的init开始被调用')
            self.age = age
            super().__init__(name, *args, **kwargs)         # 为避免多继承报错,使用不定长参数,接受参数
            print('Son1的init结束被调用')
 
    class Son2(Parent):
        def __init__(self, name, gender, *args, **kwargs):  # 为避免多继承报错,使用不定长参数,接受参数
            print('Son2的init开始被调用')
            self.gender = gender
            super().__init__(name, *args, **kwargs)         # 为避免多继承报错,使用不定长参数,接受参数
            print('Son2的init结束被调用')
    
    class Grandson(Son1, Son2):
        def __init__(self, name, age, gender):
            print('Grandson的init开始被调用')
            # 多继承时,相对于使用类名.__init__方法,要把每个父类全部写一遍
            # 而super只用一句话,执行了全部父类的方法,这也是为何多继承需要全部传参的一个原因
            # super(Grandson, self).__init__(name, age, gender) 效果和下面的一样
            super().__init__(name, age, gender)
            print('Grandson的init结束被调用')
    
    print(Grandson.__mro__)                                 # 搜索顺序
    
    gs = Grandson('grandson', 12, '男')
    
    print('姓名:', gs.name)
    print('年龄:', gs.age)
    print('性别:', gs.gender)
    
    # super调用过程:上面gs初始化时,先执行grandson中init方法, 其中的init有super调用,
    # 每执行到一次super时,都会从__mro__方法元组中顺序查找搜索。所以先调用son1的init方法,
    # 在son1中又有super调用,这个时候就就根据__mro__表去调用son2的init,然后在son2中又有super调用,
    # 这个就根据mro表又去调用parent中的init,直到调用object中的init.

# 类和对象Ⅴ
elif inis == 5:
    # Mix-in    混入(设计模式)    没啥
    class Displayer:
        def display(self, message):
            print(message)
    
    class LoggerMixin:                                      # 本来只有Displayer、MySubClass;LoggerMixin类似插件
        def log(self, message, filename="logfile.txt"):
            with open(filename, "a") as f:
                f.write(message)
        def display(self, message):
            super().display(message)
            self.log(message)
        
    class MySubClass(LoggerMixin, Displayer):
        def log(self, message):
            super().log(message, filename="subclasslog.txt")
        
    subclass = MySubClass()
    subclass.display("This is a test.")

# 类和对象Ⅵ
elif inis == 6:
    # 多态  
    print(len("wdnmd"))                     # 内里应该判断了类型再……
    print(len(["wdnmd", "cnmlch", "fuck"]))

    def func(a,b,c):
        print("a,b,c")
    def func():
        print("wdnmd")
    func(1,2,3)                             # 异常,python没有函数重载

# 类和对象Ⅶ
elif inis == 7:
    # "私有变量"    本质是换名  __name
    class C:
        def __init__(self, val) -> None:
            self.__val = val
        def __getVal(self):
            return self.__val
        def setVal(self, val):
            self.__val = val

    c = C(438)
    print(c.__dict__)
    # c.__val 、 c__getVal()  报异常
    print(c._C__val)
    
    # class类似dict用空间换时间,通过 __slots__ 固定class的空间
    class A:
        __slots__ = ['x', 'y']      # 固定就两个变量
        # def __init__(self, x, y, z) -> None:
        #     self.x = x
        #     self.y = y
        #     self.z = z          
        def __init__(self, x, y) -> None:
            self.x = x
            self.y = y
    # a = A(1,2,3)                  # 会报异常
    a = A(1,2)
    # a.z = 3                       # 不能动态添加属性,会报异常

    # 继承自父类的_slots属性是不会在子类中生效的

# 类和对象Ⅷ
elif inis == 8:
    # 魔法方法  __new__ 、__init__ 、 __del__       # 从左往右依次调用
    # __new__方法主要是当你继承一些不可变的 class 时(比如int, str, tuple),提供给你一个自定义这些类的实例化过程的途径
    class CapStr(str):
        def __new__(cls, string, *args, **kwargs):
            string = string.upper()
            return super().__new__(cls, string)
        def __init__(self, x, y, *args, **kwargs) -> None:
            super().__init__()
            self.x = x
            self.y = y
        def __del__(self):
            print("del~")

    c = CapStr("fuck", 3)
    print(c)
    print(c.x)
    print(c.y)    

# 类和对象Ⅸ
elif inis == 9:
    # 魔法方法大全  https://fishc.com.cn/thread-214869-1-7.html
    class S(str):
        def __add__(self, other:str):
            return len(self) + len(other)
            # return NotImplemented
        
    s1 = S("wdnmd")
    s2 = S("fuck")
    print(s1 + s2)
    # 注1:如果魔法方法中的某一个不支持与所提供参数进行运算,它应该返回 NotImplemented。
    # 注2:当两个对象相加的时候,如果左侧的对象和右侧的对象不同类型,并且左侧的对象没有定义 __add__() 方法,或者其 __add__() 返回 NotImplemented,
    # 那么 Python 就会去右侧的对象中找查找是否有 __radd__() 方法的定义。
    # 注3:如果增强赋值运算符的左侧对象没有实现相应的魔法方法,比如 += 的左侧对象没有实现 __iadd__() 方法,
    # 那么将退而求其次,使用相应的 __add__() 方法和 __radd__() 方法来实现。

# 类和对象Ⅹ
elif inis == 10:
    # 魔法方法 位运算   有基础,看就行
    print(bin(8))
    print(3 & 2)
    print(1 | 4)
    print(~2)       # 补码原因
    print(3 ^ 4)
    # <<    >> 

    import math     # 数字函数
    print(0.1 + 0.2 == 0.3 + math.ulp(0.3))
    print(0.1 + 0.2 == 0.3)

    # __index__
    class C:
        def __init__(self, x:int) -> None:
            self.x = x
        def __index__(self):
            print("wdnmdcnmlch")
            return self.x
        def setVal(self, x:int) -> None:
            self.x = x
            
    c = C(3)
    # c[3]  错误用法
    s = "fuck"
    print(s[c])
    c.setVal(0)
    print(s[c])

# 类和对象Ⅺ
elif inis == 11:
    from typing import Any

    # 属性访问
    class C:
        def __init__(self, name, age) -> None:
            self.name = name
            self.__age = age
        
    c = C("wdnm", 98)
    print(hasattr(c, "name"))
    print(getattr(c, "_C__age"))    # settattr  delattr     魔法方法

    class C:
        def __init__(self, name, age) -> None:
            self.name = name
            self.__age = age
        def __getattribute__(self, __name: str) -> Any:
            print("__getattribute__ wdnmd")
            return super().__getattribute__(__name)

        def __getattr__(self, __name: str):                     # 访问类没有的属性会调用此函数
            print("__getattr__ 访问异常才抛出")
        
    c = C("fuck", 130)
    print(getattr(c, "_C__age"))
    c.name
    print(getattr(c, "nokey"))
    c.cnm
    print("---------------------------------")

    class D:
        def __setattr__(self, __name: str, __value: Any):
            print("self.__name = __value    会报错,这本身也会调用__setattr__")
            return super().__setattr__(__name, __value)
        def __delattr__(self, __name: str) -> None:
            print("__delattr__ 和 __setattr__ 一样问题") 
            if ~hasattr(self, __name):
                return None
            return super().__delattr__(__name)
        
    d = D()
    d.name = "cnm"
    # d.age = 8
    print(d.name)
    del d.name
    delattr(d, "age")

# 类和对象Ⅻ
elif inis == 12:
    class C:
        def __init__(self, data: str) -> None:
            self.data = data
        def __getitem__(self, index):
            return(self.data[index])
        def __setitem__(self, index, value):
            self.data[index] = value

    c = C([1,2,3,4,5])
    print(c[2])
    c[2:4] = c[0:2]
    print(c[:])

    print(c[2::])       # slice(2, None, None)
    s = "wdnmcnmlch"
    print(s[slice(1)], s[1])                  
    print(s[slice(5, None)], s[5::])            # 语法糖 
    print(s[slice(None, None, 2)], s[::2])      

    # 自定义迭代器
    class D:
        def __init__(self, start, stop) -> None:
            self.value = start -1
            self.stop = stop
        def __iter__(self):
            return self
        def __next__(self):
            if self.value == self.stop:
                raise StopIteration    # 主动爆异常
            self.value += 1
            return self.value * 2

    d = D(1, 5)
    for i in d:
        print(i, end=' ')

# 类和对象XIII
elif inis == 13:
    # 魔法方法  in not
    class C:
        def __init__(self, data) -> None:
            self.data = data
        def __contains__(self, item):
            print("__contains__")
            return item in self.data
        # __contains__ = None     # 静止关系判断  in not 会报异常,针对所有魔法方法有效
        
    c = C([1,2,3,4,5,6,10])
    print(10 in c)          # 没有 __contains__ 就调 __iter__/__next__ 再没有就调 __getitem__

    # bool(object) ==> 无 __bool__  调 __len__ 

    # __lt__(<)、__le__(<=)、__gt__(>)、__ge__(>=)、__eq__(==)、__ne__(!=)、

# 类和对象XIV
elif inis == 14:
    from typing import Any
    # 魔法方法 __lt__(<)
    class C:
        def __call__(self, *args: Any, **kwds: Any) -> Any:
            print(f"位置参数-->{args}\n关键字参数-->{kwds}")
    c = C()
    c(438,250,w="wdnmd",f="fuck")

    # str()__str__   repr()__repr__ 两个必须返回字符串
    eval("print(\"wdnmdlch\")")
    print(repr("fuck"))                 # 返回对象的规范字符串表示形式。对于许多对象类型,eval(repr(obj)=obj。

    class C:
        def __init__(self, data) -> None:
             self.data = data
        def __str__(self) -> str:
            return  f"data = {self.data}"
        def __repr__(self) -> str:
            return f"C({self.data})"
        
    c = C(250)
    print(c)            # 无 __str__ 调 __repr__(适用更广,更稳)
	c
    

P73~P83:类和对象class and object(2)
inis = 25

# 类和对象XV
if inis == 15:
    #class property(fget=None,fset=None,fdel=None,doc=None)     property()函数用于返回一个property属性对象
    class C:
        def __init__(self):
            self._x = 250
        def getx(self):
            return self._x
        def setx(self, value):
            self._x = value
        def delx(self):
            del self._x
        x = property(getx, setx, delx)

    c = C()
    print(c.x)#250
    c.x = 520
    print(c.__dict__)#{'_x': 520}
    del c.x
    print(c.__dict__)#{}

    #利用__getattr__()、__setattr__()、__delattr__()实现相同目的    比较繁琐,也不好拓展
    #propert()函数第一个优点是简化类似遮遮掩掩的操作
        
    # property属性对象(由property函数返回,根据语法糖解析是传给了x)提供了getter、setter和deleter三个方法,这些方法对应property()函数的三个参数接口
    class E:
        def __init__(self):
            self._x = 250
        # d = property()
        #@d.getter                    
        @property                   # ==> x = property(x) (语法糖)  
        def x(self):
            return self._x
        # d = d.getter(x)  
        @x.setter                   # x = x.setter(x)
        def x(self, value):
            self._x = value
        # d = d.setter(x)
        @x.deleter
        def x(self):
            del self._x
        # d = d.deleter(x)
    e = E()
    print(e.x)              #250                  # print(e.d)
    e.x = 520
    print(e.__dict__)       #{'_x': 520}
    del e.x
    print(e.__dict__)       #{}

# 类和对象XVI 
elif inis == 16:
    # 类方法 classmethod        设计类属性、类继承用类方法好
    class C:
        count = 0
        @classmethod
        def add(cls):
            cls.count += 1
        def __init__(self) -> None:
            self.add()
        @classmethod
        def printCcount(cls):
            print(f"该类{cls.__name__}一共实例 {cls.count} 个对象")
    class D(C):
        count = 0
    class E(D):
        count = 0
    c1 = C()
    d1, d2 = D(), D()
    e1, e2, e3 = E(), E(), E()
    c1.printCcount()
    d1.printCcount()
    e1.printCcount()

    # 静态方法 staticmethod     不涉及类属性的操作用静态方法好
    class C:
        count = 0
        def __init__(self) -> None:
            C.count += 1
        @staticmethod
        def printCcount():                              #普通方法self(自己的类对象),类方法cls(传进来的类对象),静态方法不需要参数
            print(f"该类C一共实例 {C.count} 个对象")
    c1, c2 = C(), C()
    c2.printCcount()
    
# 类和对象XVII 
elif inis == 17:
    # 描述符    实现__get__、__set__、__delete__魔法方法的类就为描述符      
    class D:
        def __get__(self, instance, owner):         # 三个方法主要用instance参数    :被描述符拦戳的属性所在的类的实例对象
            return instance._x
        def __set__(self, instance, value):
            instance._x = value
        def __delete__(self, instance):
            del instance._x

    class C:
        x = D()
        def __init__(self, x = 250) -> None:
            self._x = 250
        
    c = C()
    print(c.x)
    c.x = 438
    print(c.x)
    print(c.__dict__)
    del c.x
    print(c.__dict__)

    # 用property更好,先有描述符后有 property
    # 用描述符实现property;用描述符实现__getattr__()、__setattr__()、__delattr__()

# 类和对象XVIII
elif inis == 18:
    # 描述符只作用类属性,不作用对象属性self.name
    # 描述符访问顺序由低到高,数据描述符(只实现__get__),实例对象属性,非数据描述符(实现__set__、__delete__),类属性
    # 描述符第四个魔法方法__set_name__(py3.6)   为了优雅
    class D:
        def __set_name__(self, owner, name):
            self.name = name
        def __get__(self, instance, owner):
            print("get~")
            return instance.__dict__.get(self.name)
        def __set__(self, instance, value):
            print("set~")
            instance.__dict__[self.name] = value
        def __delete__(self, instance):
            print("del~")
            del instance.__dict__[self.name]

    class C:
        x = D()
    c = C()
    print(c.__dict__)
    c.x = 250
    print(c.__dict__)
    print(c.x)
    del c.x
    print(c.__dict__)

# 类和对象XIX
elif inis == 19:
    # 解读官方文档:python怎么区分函数和方法(class);(通过描述符)
    pass

# 类和对象XX
elif inis == 20:
    from typing import Any
    # 作用于类的装饰器
    print("------------------作用于类的装饰器")
    def report(cls):
        def oncall(*args, **kwargs):            
            print("开始实例化对象")
            _ = cls(*args)                      # args = (1,2,3)
            print("准备返回实例对象")
            return _
        return oncall

    @report                                     # C = report(C)
    class C:
        def __init__(self, x, y, z) -> None:
            self.x = x
            self.y = y
            self.z = z
            print("初始化类中")

    c = C(1,2,3)
    print(c.__dict__)

    # 类装饰函数
    print("------------------类装饰函数")
    class Counter:
        def __init__(self, func, count = 0) -> None:
            self.count = count
            self.func = func
        def __call__(self, *args: Any, **kwds: Any) -> Any:
            self.count += 1
            print(f"函数调用{self.count}次了")
            return self.func(*args, **kwds)

    @Counter                                  # printCount = Counter(printCount)
    def printCount():
        print("wdnmdlch, fuck")
    printCount()
    printCount()
    printCount()

    # 类装饰类
    print("------------------类装饰类")
    def report(cls):
        class Check:
            def __init__(self, *args, **kwargs) -> None:
                self.obj = cls(*args, **kwargs)
            def __getattr__(self, name):                # 访问类没有的属性会调用此函数
                print(f"正在访问{name}...")
                return getattr(self.obj, name)
        return Check
    
    @report                                             # C = report(C)
    class C:
        def __init__(self, name) -> None:
            self.name = name
        def say_hi(self):
            print(f"hi{self.name}~")
        def say_hey(self):
            print(f"hey{self.name}~")

    c1 = C("c1")                                        # 顺序:(Check)__init__、(C)__init__
    c2 = C("c2")
    print(c1.name)                                      # (Check)__getattr__、getattr(c1, name)
    print(c2.name)
    c1.say_hi()
    c2.say_hey()

    print(type(c1))

# 类和对象XXI 
elif inis == 21:
    # type() 返回class    class 是由 type 创造而来的
    type(250)("250")            # int("250")
    type("wdnmd")(7438)
    class A:
        pass
    print(type(A))

    # type()建立类  type()文档:https://fishc.com.cn/thread-220218-1-8.html
    class C:
        pass
    C = type("C", (), dict(x=250, y=438))
    c = C()
    print(c.x)

    class D:
        pass
    def func(self, name):
        print(f"wdnmdlch, fuck{name}", self.a)
    D = type("D", (C,), dict(a="wdnmd", b=func))
    d = D()
    print(d.x, d.a)
    d.b("8.8")

    A = type("R",(), dict(z=1314))
    a = A()
    print(a.z, type(a))

    # __init_subclass__ python3.6,增强父类对子类的控制                子类 __init__ 能摆脱
    class C:
        def __init_subclass__(cls, val1, val2) -> None:
            print("__init_subclass__")
            cls.val1 = val1
            cls.val2 = val2
        pass
    class D(C, val1=250, val2=438):
        val1 = 520
        val2 = 1314
        # def __init__(self, val1, val2) -> None:
        #     print("__init__")
        #     self.val1 = val1
        #     self.val2 = val2
    d = D()
    print(d.val1, d.val2)

    # type() 最后一个参数   __init_subclass__
    class A:
        def __init_subclass__(cls, value) -> None:
            cls.value = value
        pass
    class B:
        pass
    B = type("B", (A,), dict(value=520), value=250)     # type()参数:类名、父类、类属性(变量,方法)、__init_subclass__
    b = B()
    print(b.value)

# 类和对象XXII
elif inis == 22:
    from typing import Any
    # 元类 metaclass(type是所以元类的父类也是元类)(难,用得少)是创造类的模板
    # 元类主要通过 __new__ 、 __init__ 、 __call__ 魔法方法工作
    class MetaC(type):
        def __new__(mcls, name, bases, attrs):                                      # name为类名,bases为父类,attrs为类里面的属性和方法
            print("MetaC __new__:", f"mcls={mcls}, name={name}, bases={bases}, attrs={attrs}")
            return type.__new__(mcls, name, bases, attrs)
        def __init__(cls, name, bases, attrs):
            print("MetaC __init__:", f"cls={cls}, name={name}, bases={bases}, attrs={attrs}")
            return type.__init__(cls, name, bases, attrs)
        def __call__(cls, *args: Any, **kwds: Any) -> Any:
            print("MetaC __call__:", f"args={args}, kwds={kwds}")
            # return type.__call__(cls, *args, **kwds)

    class B:
        pass
    class C(B, metaclass=MetaC):
        def __new__(cls):
            print("C __new__:", f"cls={cls}")
            return super().__new__(cls)
        def __init__(self) -> None:
            print("C __init__:", f"self={self}")

    c = C(123, 321, x=520, y=1314)
    # c = C()                             # 把 MetaC __call__ 注释了
    # 类C创建完成 调用MetaC __new__、__init__,而MetaC的 __call__ 会截胡掉C的实例化操作(__new__、__init__)

# 类和对象XXIII 
elif inis == 23:
    from typing import Any
    # 元类在实际开发中的作用
    # 给所有的类添加属性、 对类名的定义规范做限制、修改对象的属性值、限制类实例化时的传参方式、禁止一个类被实例化、只允许实例化一个对象

    class MetaC(type):
        def __init__(cls, name, bases, attrs):          # 大部分在 __new__ 内也可完成 
            # 给所有的类添加属性、
            cls.author = "Sr"
            # 对类名的定义规范做限制
            if not name.istitle():
                raise TypeError("类名必须为大写~")
            # 只允许实例化一个对象(1)
            cls.__instance = None
            return type.__init__(cls, name, bases, attrs)

        def __call__(cls, *args: Any, **kwds: Any) -> Any:
            # 修改对象的属性值 -> 如:把对象的所有字符串属性值都变成大写
            new_args = [each.upper() for each in args if isinstance(each, str)]
            # 限制类实例化时的传参方式
            if kwds:
                raise TypeError("只能位置参数传参~")
            
            # 只允许实例化一个对象(2)
            if cls.__instance is None:
                cls.__instance = type.__call__(cls, *new_args, **kwds)
                return cls.__instance
            else:
                return cls.__instance  
        
    # 禁止一个类被实例化        做成单例类一样
    class NoInstances(type):
        def __call__(self, *args, **kwargs):
            raise TypeError('该类禁止实例化!')
    class C(metaclass=NoInstances):
        @classmethod
        def funcClass(cls):
            print("类方法可调用~")

        @staticmethod
        def funcStantic():
            print("静态方法可调用~")
        pass
    # c = C()
    C.funcClass()
    C.funcStantic()

    class C(metaclass=MetaC):
        def __init__(self, name) -> None:
            self.name = name

    c = C("wdnmd")
    c2 = C()
    print(c.author)
    print(c.name)
    print(c is c2)
    # c = C(name="123")
    # class e(metaclass=MetaC):
    #     pass

# 类和对象XXIV
elif inis == 24:
    # 抽象基类 编程规范的实施手段
    from abc import ABCMeta, abstractmethod

    class Fruit(metaclass=ABCMeta):
        def __init__(self, name) -> None:
            self.name = name
        @abstractmethod                 # 继承的类必须实现此方法;类不能直接实例化;metaclass=ABCMeta的类才能用此装饰
        def good_for_health(self):
            pass
    # f = Fruit("pitaya")               # 报错异常        
    class Pitaya(Fruit):
        def __init__(self, name) -> None:
            super().__init__(name)
        def good_for_health(self):
            print("10块钱5个~", self.name)

    p = Pitaya("火龙果")
    p.good_for_health()

# 类和对象XXV
elif inis == 25:
    # 探讨
    # python的 import 模组学习:https://fishc.com.cn/forum-319-1.html
    pass

P84~P86:模块和包modules and packages
inis = 3

# 模块和包↑
if inis == 1:
    # 模块是python中最高级别的组织结构      而包是一个模块的集合,可以将多个模块的功能组合到一起,同时还可以包含其他子包
    # python高校开发主要就是导包,根据需求选择导入包    (.py其实就是一个包)    
    
    # 三种导入模块的方式 
    # import 模块名称
    # from 模块名称 import 对象名称
    # import 模块名称 as 关联名称
    import modules.hello
    from modules.hello import *                 # say_fuck  # 对于包来说,如果没有定义__all__,那么 from...import * 的语法则不导入包里面的任何模块。
    from modules.hello_for_diu import *
    import modules.hello_for_diu as h           # 模块内重名,有标识》导入顺序(最后导入的优先)

    modules.hello.say_wdnmd()
    say_fuck()
    h.say_fuck()

# 模块和包-
elif inis == 2:
    # if(__name__ == "__main__") 看modules/pc.py
    from modules.pc import cTof as c, fToc as f
    print(f"{c(39):.2f}")
    print(f"{f(39):.2f}")

    # 包    python3.3之前需要在包文件夹内创建__init__.py文件
    # 编写 __init__.py 对包进行初始化操作
    import package
    print(package.x, package.y)
    package.pc.printX()

    # __all__ 
    # 对于模块来说,如果没有定义__all__属性,那么 from...import * 的语法将导入模块中的所有东西:
    # 对于包来说,如果没有定义__all__,那么 from...import * 的语法则不导入包里面的任何模块。 
    from modules.hello import *
    say_wdnmd()
    # say_fuck()            # 会异常

    from package import *
    pc.printX()

# 模块和包↓
elif inis == 3:
    # 上传代码模块、包到pipy分享
    pass

推荐阅读

https://blog.csdn.net/weixin_45068267

  • 19
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值