book_effective Python_59个有效办法(一)

1 确认python版本

2 PET 8风格

PEP 8是对Python代码格式而编订的风格指南。

空白(whitespace)

  • 使用space(空格)来表示缩进,而不是tab(制表符)
  • 每层缩进4个空格
  • 每行字符不超过79
  • 多行长表达式,除首行外要再缩进4个空格
  • 函数与类之间用两个空行隔开
  • 同一个类中,各方法用一个空行隔开
  • 下标获取列表元素、调用函数或给关键字参数赋值的时候,不要在两旁添加空格
  • 赋值符号左右两侧各一个空格

    命名

  • 函数、变量及属性应该用小写字母来拼写,单词间以下划线相连
  • 受保护的实例属性,以单下划线开头,例,_leading_underscore
  • 私有的实例属性,以双下划线开头,例,__double_underscore
  • 类、异常,每个首字母大写,例,CapitalizedWord
  • 模块级别的常量,全大写且以下划线相连,例,ALL_CAPS
  • 类中的实例方法,首个参数名为 self,以表示该对象自身
  • 类方法,首个参数名为 cls,以表示类自身

    表达式和语句

  • 采用内联形式的否定词,例,if a is not b 而不是 if not a is b
  • if not somelist 而不是 if len(somelist)==0。空值自动评估为False
  • if somelist 默认会把非空值判断为True
  • 不要编写单行的if、for、while、excep语句
  • import 放在文件开头
  • 引入模块应使用绝对名称,例,from bar import foo 而不是 import foo
  • 若一定以相对名称来编写import语句,应采用明确地写法:from.import bar
  • import顺序:标准库、第三方、自用 三部分模块。各部分按字母排序

3 了解bytes、str与Unicode的区别

没看懂

4 用辅助函数来取代复杂的表达式

if/else表达式比or或and写成的表达式清晰

5 了解切割序列的办法

  • 基本切片操作: somelist[start:end],且含start,不含end。
  • 切割列表时不计较索引是否越界。这可用于限定输入序列的最大长度,例如、,a[:20]或a[20:]。访问列表时,下标不可越界
  • 切割后,会产生另外一份全新的列表。新列表的修改,不会影响原列表。
b=a[:] #b is not a
c=a #c is a

6 单词切片操作内,不要同时指定start、end和stride

  • 进式切片: somelist[start:end:stride]。可以指定步进值(stride)
  • stride 可以为负,但尽量避免。-1可反转list。
  • 不要同时使用start、end和stride。可以拆解成两条:一条做范围切割,一条做步进切割,或考虑内置itertool模块中的islice。

7 用列表推导来取代map和filter

列表推导(list comprehension):根据一份列表来制作另一份。同时指定索要迭代的输入序列,以及计算新列表中每个元素的值所用的表达式。

a=[1,2,3,4]
s1=[x**2 for x in a]
>>> [1,4,9,16]
s2=[x**2 for x in a if x % 2 == 0]
>>>[4,16]

字典(dict)和集(set)也有和列表类似的推导机制

cr={'g':1,'h':2}
rc={r:c for c,r in cr.items()}
ls={len(n) for n in rc.values()}
print (rc,ls)
>>>({1: 'g', 2: 'h'}, set([1]))

8 不要使用含有两个以上表达式的列表推导

列表推导支持多重循环。

例如,把矩阵(列表的列表)简化为一维列表

m=[[1,2],[3,4]]
f=[x for row in m for x in row]
print (f)
>>>[1,2,3,4]

例如,

s=[[x**2 for x in row] for row in m]
>>>[[1, 4], [9, 16]]

列表也支持多个if条件

fi=[x for x in f if x>2 if x % 2==0]`
print (fi)
>>>[4]
  • 列表推导支持多级循环,每一级循环也支持多项条件
  • 超多两个表达式的列表推导是很难理解的,应该尽量避免。

9 用生成器表达式来改写数据量较大的列表推导

数据大较大,列表推导可能会占用过多的内存。由生成器表达式所返回的迭代器,可以逐次产生输出值,避免内存用量的问题。

#将列表推导的中括号改成小括号,就成了生成器的表达式
it=(len(x) for x in open ('my_file.txt'))  
#it是一个迭代器
#逐次调用内置的next函数,返回迭代器对应的参数
print (next(it))#输出下一个值
print (next(it))#输出下一个值

10 enumerate 取代range

既要元素,还要索引时,

for i in range(len(somelist)):
    s=somelist[i]
#另一种实现方式,n可指定开始计数的值,缺省为0
for i,s in enumerate (somelist,n):
    pass

enumerate 可把迭代器包装成生成器,生成器每次产生一对输出值,前者表示下标,后者表示序列元素。

11 zip函数遍历两个迭代器

names=['abc','defg']
ls=[len(n) for n in names]
for name, l in zip (names, ls):
    pass 
  • Python 3 中的zip相当于生成器,会在遍历过程中逐次产生元组,而Python 2 则是直接把这些元组完全生成好,一次返回。
  • 迭代器长度不等,zip就会提前终止
  • itertools内置模块中的zip_longest ( Python 2 中为izip_longest)

12 不在循环后写else块

  • 语法上,for和while循环后,可以紧跟else块。循环没有遇上break时,else才会执行
  • 尽量不要使用else块

13 合理利用try/except/else/finally

  • 无论try块是否发生异常,都可用finally块来执行清理工作
  • try块没有发生异常,就执行else块,可执行在代码清理(finally块)前的操作
  • except块针对可能发生的异常,分别执行相应的操作
def ljk(data,key):
    try: 
        r=j.loads(data)
    except ValueError as e :
        raise KeyErro from e   #这句啥意思?
    else:
        return r[key]
  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值