2020.6.15 python知识补充

发布于 2020-06-14  75 次阅读


Table of Contents

  • 保证多线程,同时只执行一个线程
  • GIL的问题,是python解释器的问题
  • java的python解释器中没有GIL解释器
  • 参考:
  • python调用C语言

    • from ctypes import *
      from threading import Thread
      lib = cdll.LoadLibrary("./libdead_loop.so")
      t = Thread(target=lib.DeadLoop)
      
      # libdead_loop是c编译过的代码,里面是一个函数,DeadLoop执行死循环
      
      t.start()
      t.join()

  • python中深拷贝,浅拷贝

    • python是引用型变量(就是变量空间存储的是变量的地址)
    • 浅拷贝就是变量指向一块地址
    • 深拷贝就是变量里面的引用被提取出来,放到一块地方,从新赋值给变量
    • copy模块中两个方法copy.copy,copy.deepcopy

      • 默认赋值操作是浅拷贝
      • 浅拷贝只拷贝一层,深拷贝全部拷贝为新的
      • 简单描述深浅拷贝
        • 浅拷贝,把地面上的树拿走
        • 深拷贝,把书连着根一起拿走
      • 注意点:
        • a和b都是列表
          • a=b //相当于 把b的引用值赋值给a
          • a.copy.copy(b) 把b内元素的引用值给a
        • a和b都是元组
          • 如果是不可变数据组成的元组,用copy和deepcopy函数则都不拷贝,直接指向元组
          • 如果元组中有可变数据,则deepcopy会将其中元素拷贝出来
          • 元组 += 是新生成了一个元组,重新赋值
          • +=等操作,是被python优化过的
    • 列表的切片也是拷贝

      • 切片是浅拷贝,同copy.copy()
      • 切片是拷贝列表元素内的数据
    • 字典拷贝

      • 字典.copy() 是浅拷贝
      • 字典.deepcopy() 是深拷贝
    • python中传递实参

      • 传递实参的时候,传递的都是引用
      • 传递实参,就是copy.copy 所以会被改变,而deepcopy则不会被改变
  • python私有化

    • xx:公有变量
    • _xx:单只下划线,私有化属性,from * 不能导入,类对象和子对象可以访问
    • __xx:双下划线,避免子类中的属性名冲突,外部无法直接访问(名字重整,外部无法访问)
    • __xx__:双下划线,用户名,空间魔法对象或属性
    • xx_:后置单下划线,避免和python关键字冲突
    • 名字重整(name mangling)目的防止子类意外重写基类方法或属性,访问需要_ClassName__.变量或者方法变量
  • python 导入方式

    • import 包名 导入时候做了两件事

      • 首先导入 包名
      • 在py文件中定义,赋值指向模块( 包名 = 指向模块)
    • 导入路径

      • sys.path 中存放了所有寻找路径,只要寻找到一个,立马停止搜索,执行命令
      • 如果需要导入,可以在sys.path中插入一条目标,插入最开始,代表优先搜索
      • 导入时候,有一个特点,import会防止重复导入,所以如果导入模块有变化,需要reload函数重新加载模块(from imp import reload)
      • reload 只能用在import上,并且reload必须要在import导入之后才能使用
      • python中help()函数,可以查看文档
    • from和Import的坑

      • from 导入的内容,相当于全局变量,如果需要修改,需要添加global
        • from * import num
        • 如果num是一个常量,则不会被改变,如果num是可变的,则可以修改(append)
        • from导入相当于模块内定义一个变量num(全局变量),指向了导入模块num的值,如果当前模块内赋值,则是把这个变量a的指向改变为新的值,global修改是相当于在全局修改模块内num的值
      • import 导入的内容,模块名.变量 可以改变变量
        • import相当于定义一个变量,指向了那个模块,所以可以修改模块内的值
  • python 封装,继承,多态

    • python中都是对象,类也是一个对象
    • 对象就相当一个小作用域,里面变量,方法都是分离的(看着分离,实际指向class)
    • 创建对象的时候,有一个特殊的属性__class__,可以找到模板,模板里面的方法就是共用的
    • __dict__中就是对象中定义的属性,方法(self的属性方法),
    • 为什么要封装?

      • 1.函数式编程,对数据处理很繁琐,需要数据来回调用,混乱
      • 2.封装之后,代码划分更清晰
    • 为什么要继承?

      • 没有继承,代码冗余
      • 没有继承,无法描述对象之间的关系
      • 继承可以调用抽象方法
      • 重用方法,属性
    • 为什么要多态

      • 继承和多态往往结合使用
      • 多种形态,子类重写了,就调用子类,没有重写,就调用父类
      • 调用父类,可以传递子类
  • 多继承MRO顺序

    • 多继承定义

      • 一个类,继承多个类
      • 继承不是复制,是一个指针,指向了父类的变量或者方法
      • MRO c3算法
    • 多继承难点 super

    • MRO

      • 类继承是按照MRO
      • 类中的方法属性查找也按照MRO
    • 调用父类方法(三中方法)

      • 父类名.方法名(self,参数)
        • 一个继承,就调用一次,顶层类,被调用多次
        • 简介明了,但是会被调用多次(比如open最多1024个),多次调用就占用了资源
      • super(父类名,self.方法名(参数))
        • 多级承中,子类使用中只调用 子类类名.__mro__中的第一个父类(子类,父类。。父类,object)
        • 调用完子类,在父类中如果还要 super(父类名,self.方法名(参数)) 这时调用的是子类的__mro__第二个父类
        • super(父类,self.方法名(参数)) 拿父类名在mro中查找
        • __mro__中是继承的所有父类
      • super().方法名(参数)
        • 不需要self参数
        • 拿当前类的类名去mro中查找
        • 和super(父类名,self.方法名(参数))基本一样
      • 总结
        • super().__init__()和类名.__()__调用,单继承上无差别
    • 重载,重写的区别

      • 重载:
        • 方法名称一样,形参的类型不一样,java有重载
        • 根据调用方法形参不同,来决定执行哪个方法
      • 重写(覆盖)
        • 方法名称一样,
          • 后定义的会覆盖先定义的,
          • 父类函数被子类的覆盖
  • python 对象

    • __dict__

      • 类调用就是类属性
      • 实例对象调用就是实例对象的属性
    • python中对象创建

      • 创建对象的过程
        • 类对象
          • 类属性在内存中只保存一份
          • 类本身也是一块内存空间,存放了类方法,类属性
        • 实例对象
          • 实例对象在内存中可以有多份
          • 实例对象,__class__ 指向类的对象地址
          • __new__ 创建对象:创建一个内存空间
          • __init__ 对申请的空间,进行初始化
    • 类(类对象)
      • 实例方法,静态方法,和类方法,都是属于类
        • 实例方法(self)需要一个self,指向实例对象,通过类.方法调用
        • 类方法:类调用 需要cls属性,指向类对象,可以修改类属性的方法
        • 静态方法:由类调用,无默认参数
    • 实例对象(类对象生成的对象)
      • 在实例对象中定义的属性或方法,
        • 如果和类重名,则直接调用实例方法中的属性或方法
        • 如果实例中没有,则取类中查找
  • Property属性的使用

    • 作用:
      • 通过 方法.属性 来调用方法,(注意没有括号)
      • 可以通过这种方法限定值的规则,类型(数字长度,只能是数字,每次调用-1)
    • 使用方法:
      • @property修饰方法
      • 方法中不能有属性(只能是self)
      • 和普通方法唯一不同的就是少了扩号,而括号容易让人疑惑是否需要传参
      • 封装使用的体现
    • 两种定义property的方法
      • 装饰器创建方法
        • 经典类(快被淘汰)
          • python 需要手动继承(object)
          • 只能使用@property
        • 新式类
          • python默认继承了object()
          • @property
            • 函数名就是调用的名
            • 需要一个返回值
          • @name.setter
            • 函数名就是调用的名
            • 需要一个参数
          • @name.deleter
            • 函数名就是调用的名
            • del 触发这个函数
      • 类创建方法
        • property(传递一个方法)类
        • property有四个参数
          • 前三个参数都是方法名 ,分别是获取,赋值,删除时候被调用(按照顺序)
          • 最后一个参数是 __doc__ 文档说明,描述信息
  • Javascript 数组

    • 两种定义方法:
      • 稀松数组:数组不是每位都有值
      • arr=[]
      • arr = new Array()
  • 5.知识内容个人梳理

    6.今天都复习了之前的什么内容