Python高级笔记

用Python很多年,可感觉学的比较碎片,整理下之前的笔记。 学而时习之。

类和面向对象

new()构造器可以实例化不可变对象,必须返回一个合法的实例

实例属性和类属性:

  • 两种不同属性,类属性和实例无关
  • 不要从实例修改可变的类属性
  • 类属性的修改会影响所有实例

类变量使用场合:

  • 用做常量: 被所有实例使用. 对于类变量的修改,会反映到所有实例.
  • 方便通过类直接访问

变量的查找顺序为: 实例 > 类 > 基类

绑定binding:

  • 没有实例时方法就是未绑定的
  • self用于类实例方法中引用方法所绑定的实例
  • 还没有实例且需要调用一个非绑定方法时必须传递self, 比如覆盖父类方法

静态方法和类方法

  • @classmethod: 函数参数是类对象而不是实例对象. 如果涉及工厂方法,应该使用类方法而不是静态方法.
  • @staticmethod: 通常,有很多情况下一些函数与类相关,但不需要任何类或实例变量就可以实现一些功能.
  • mixin 类:对两个完全不相关的类进行多重继承(联合)

如果需要在多个模块共享全局变量,通常使用模块如config.py实现.因此模块是单例设计模式的基本实现.

新式类的高级特征

  • __slots__类属性
  • 描述符
    • get(), set(), delete()
    • getattribute()特殊方法
    • 优先级别
      • 类属性
      • 数据描述符
      • 实例属性
      • 非数据描述符
      • 默认为__getattr__()
    • 属性和@property
  • 元类和__metaclass__

区别:

  • getattr(): 获取属性;内建getattr();仅当属性没有找到时调用
  • getattribute(): 获取属性;内建getattr(); 总是被调用

与类相关模块:

  • UserList, UserDict, UserString
  • types
  • operator

函数式

iterator

  • itertools.islice

高级特性

Context Manager

from contextlib import contextmanager

@contextmanager
def tag(name):
    # 必须返回一个generator类型的iterator对象
    yield

其他

内存模型

  • 不可变: 一旦一个对象被定义,他的值就不能再被更新的,除非创建新对象。
  • 参数如何传递? 总是使用引用
  • 关于拷贝: 非容器类型没有被拷贝一说,浅拷贝是用完全切片操作来完成的。

执行其他Python文件

  • python -c “import http.server; http.server.test()”
  • 执行作为脚本的模块 $python -m http.server
  • 注: 2.7对应 python -m SimpleHTTPServer

代码对象

  • compile(string, file, type) 生成字节码预编译, type: ’eval’, ‘single’, ’exec’ 之一
  • eval() 对表达式求值, 例如 input() == eval(raw_input())
  • exec obj

MonkeyPatch

动态语言的特性, 在运行时动态替换属性/方法. 经常用来在测试中替代外部资源依赖,也可以使用Mock.

from SomeOtherProduct.SomeModule import SomeClass
def speak(self):
    return "ook!"
SomeClass.speak = speak

ctypes

支持的Python内置类型:None, integers, longs, byte strings, unicode strings

  • None 作为C空指针传递
  • byte strings and unicode strings are passed as pointer to the memory block that contains their data (char * or wchar_t *).
  • Python integers and longs are passed as the platforms default C int type, their value is masked to fit into the C type.
  • create_string_buffer / create_unicode_buffer() 创建可变内存块
  • 类转为自定义类型: self.as_parameter = number 或使用property()
  • 指定参数格式 func_name.argtypes = [,,]
  • from_param()实现类方法
  • 返回类型 : 默认为int, 用.restype 指定其他类型
  • 传递指针: byref (更高效)/ pointer(会构建指针)
  • 定义的类是Structure或Union的子类,定义的_fields_ 必须是 a list of 2-tuples 包含名字和类型
  • 回调: CFUNCTYPE(返回类型)
  • 访问动态库的值 type.in_dll(pythonapi, )

扩展阅读