这些常见的 python 编码习惯,你都会吗
简介
语言在发展和变化,编码习惯也在发生改变。这里简单聊聊 17 个 python 中常见的编码习惯或者风格。
1,可变数据结构: 注意在函数变量不要使用它
1.1 模块的循环导入
我们定义一个老王模块,再定义一个小李模块,相互导入时,将报错
导入问题,如果在使用其他语言 比如 shell 脚本引用 python 代码时,需要将 python 项目加入 linux 环境变量。 <=python2.7
或者编辑 python 虚拟环境,添加 setup.py, 然后执行 python install -e .
1.2 基础规则
该次执行不缓存 sys.stdout,直接输出控制台
执行时带参数 m,以 Script 方式执行 py 模块
跳过 py 模块第一行,允许使用非 unix 形式
实体具体选项(set implementation-specific option)
程序读取文件内容并执行
程序从 stdin 读取
python3 --help # 显示所有参数
dd
2, 内存管理
python 内存回收 基于 引用计数 和 分级回收。
2.1 小的整数 和短小字符,python 将缓存以便重复使用
并且 is 关键字,用于判断两个引用所指对象是否相同
== 只判断值是否相同
2.2 对象引用时 python 基本构成方式
赋值的本质 a=1,实际上时修改 globals()字典的值,局部变量值的修改 locals()的访问和修改
2.3 引用对象 reference count
sys.getrefcount() 查看对象的引用计数,sys.getrefcount()在查看某个引用时将创建一个临时引用,所以引用计数将多 1
getrefcount© #这里 c 只有一次引用,但是计数时 2,因为当前查询有一次临时引用
引用计数的减少和增加
getrefcount© # 增加引用 d,计数 3
del d #删除引用 d,c 的引用计数又重新为 2
2.4 垃圾回收机制 garbage collection
垃圾回收时 py 独占进行的,大大降低 py 效率,特定条件下自动启动垃圾回收。
手工回收 gc.collect()
py 运行时分配对象 obj allocation 和取消分配对象 deallocation 次数被记录,高于垃圾回收阈值,启动垃圾回收
gc.get_threshold()查看该阈值,gc.set)threshold()重新设置该阈值
(700, 10, 10) 700 表示启动垃圾回收阈值,10,10 表示分别回收的阈值
2.4.1 垃圾回收分代策略 generation,基本假设如下
存活时间越久,越不可能在后面程序中变为垃圾。 这样所有对象分为 0,1,2 三代,所有新建对象都是 0 代。某一对象经历垃圾回收,仍然存活,那么它就被归入下一代对象。
垃圾回收时,一定扫描 0 代对象,如果 0 代经过一定次数垃圾回收,下一次对 0 代和 1 代扫描清理,
当 1 代也经历一次次数垃圾回收,这启动 0,1,2 所有对象的扫描
以上 gc.get_threshold()返回(700,10,10)两个表示每 10 次 0 代垃圾回收,将配置 1 次 1 代垃圾回收,每 10 次 1 代垃圾回收,才有 1 次 2 代垃圾回收。
2.4.2 两个对象相互引用,
相互引用构成引用环 reference cycle,该引用环将给上一节 2.4.1 的垃圾回收带来困难,
引用环可能构成一些无法使用但引用计数不为 0 的对象 为了回收该引用环对象,
py 复制了每个对象的引用计数为 gc_ref 遍历所有对象,将每个对象引用的对象相应的 gc_ref 减 1,遍历结束后,
gc_ref 不为 0 的对象和这些对象的引用对象,以及继续更新下游引用对象,被爆了,其他对象被回收。
参考 内存管理,函数默认参数,动态类型
2.4.3 迭代
可迭代对象 iter
迭代器 iter + next
生成器 特殊迭代器 yield
2.4.4 抽象方法*(函数)
对象方法(self.对象方法),类方法(@classmethod),静态方法(@staticmethod)
抽象方法 需要子类实现的方法 用 @abc.abstractmethod 以及 metaclass = abc.ABCMeta 使得任何继承自父类的子类必须覆盖实现抽象方法,否则抛出异常
3,其他概念
闭包 closure
闭包指的是 难以读取其他函数内部遍历的函数
实现: 定义在函数内的内部函数可以读取外层函数变量,从而实现闭包
4,惯例
1,判定 dict 的 key 是否存在,使用 key in dict 而不用 has_key
2,not 的位置,使用 key not in dict 而不用 no key in dict
3, 使用 dict.get(key[,default])如果 key 存在,返回,否则返回 default
4, 数组字典初始化
迭代一个数组,使用 for i,e in enumerate(array) 而不是 for i in range(len(array))
5,py3 元组 unpack
6, 函数参数传入
foo(**adict) #字典 key 作为参数名传入参数值
7, 字符串连接
8, 解释器中的
9,嵌套列表推导式
10, print 重定向
11,反射
12,Picking 是 Python 数据结构的序列化过程
存储一个对象,稍后再取出读取
如何 pickle 已存在的对象类型到文件
取出
pickler 内建类型和外部方法
类自定义行为
Slate 记住它曾经是什么,以及什么时候赋值给它 ?
为对象类 提供限制,只能赋予固定的属性名称
13,对象模型 Python3 和 Python2.x 之间的主要区别
Python3 的 string 和 unicode 区别不复存在,因此__unicode__被取消 __bytes__加入进来(与 python2.7 的__str__和__unicode__行为类似),用于心的创建字节数组的内建方法
py3 默认除法变成了 true 除法,因此__div__取消
__coerce__被取消,因为与其他魔法方法有功能重复 cmp 取消,与其他魔法方法功能重复__nonzero__被重命名为
bool
14,断点
15, 依赖问题
pycurl 需要 contos 7 安装 python3-devel 具体过程 pycurl-centos7
16, py 编译 发布流程
1,编译生成 pyc 文件,建议增加-O 优选项
python3 -O -m compileall -b .
2, 删除 py 文件
3, 删除__pycache__目录
4, 打包 tar 包
5, 或 git push 到仓库
16 常用内置 魔法函数
iter # 在类中实现,可以直接对类进行迭代 类似于如下形式
call # 在对象直接 进行调用
slate 为对象类 提供限制,只能赋予固定的属性名称
通过类字典返回函数,不会 返回函数名
通过类实例的点运算 查看函数 将直接返回函数
查看实例的函数对象
17 内置函数 二进制运算
文章转载自:华为云开发者联盟
评论