pythonic 代码_如何编写Pythonic的代码?

如果说优雅也有缺点的话,那就是你需要艰巨的工作才能得到它,需要良好的教育才能欣赏它。

—— Edsger Wybe Dijkstra

什么是所谓的Pythonic呢?

我发现这是一个很常见的名词,但是又很难去用纯粹理性的描述去表达。生活里有很多这样的词汇,譬如生命,我们与之日常相伴,却并不能准确拿捏定义。

Pythonic是一个很模糊的定义,甚至更接近于口语。很多年前我们说过很黄很暴力,后来演进一步,更多地使用名词形容词化,譬如“这很知乎”、“这很百度”,以及“这很中国”之类。因此Pythonic,可以换一种表达,“这很Python”。

演绎出“Pythonic”这个名词是Python语言的骄傲,表征着其不止是依赖于丰富的社区而使开发者愉悦,Python Style也作为某种标准向计算机科学界输出价值观。

在此以前,我们听说过C风格,C++风格,Java风格。与Python类似广泛流行而并未形成优雅编码风格的一门语言,叫做PHP。

这篇文章前前后后写了三个多月,为此我积累了很多可以认为是Pythonic的案例,这篇文章谨作为一个总结。

遍历:

## Bad 列举

for i in [0, 1, 2, 3, 4, 5]:

print i**2

## Better 使用range

for i in range(6):

print i**2

colors = ['red', 'green', 'blue', 'yellow']

## Bad 通过key遍历

for i in range(len(colors)):

print colors[i]

## Better 使用in直接获取value

for color in colors:

print color

colors = ['red', 'green', 'blue', 'yellow']

## Bad 通过key遍历

for i in range(len(colors)-1, -1, -1):

print colors[I]

## Better 使用in直接获取value

for color in reversed(colors):

print color

colors = ['red', 'green', 'blue', 'yellow']

## Bad 通过key遍历

for i in range(len(colors)):

print i, '--->', colors[i]

## Better 使用enumerate获取 key-value 对

for i, color in enumerate(colors):

print i, '--->', color

names = ['raymond', 'rachel', 'matthew']

colors = ['red', 'green', 'blue', 'yellow']

## Bad 通过key遍历

n = min(len(names), len(colors))

for i in range(n):

print names[i], '--->', colors[i]

## Better 使用 zip 函数

for name, color in zip(names, colors):

print name, '--->', color

排序

colors = ['red', 'green', 'blue', 'yellow']

# 正序

for color in sorted(colors):

print(color)

# 逆序

for color in sorted(colors, reverse=True):

print(color)

# 自定义排序

colors = ['red', 'green', 'blue', 'yellow']

def compare_length(c1, c2):

if len(c1) < len(c2): return -1

if len(c1) > len(c2): return 1

return 0

print sorted(colors, cmp=compare_length)

print sorted(colors, key=len)

终止循环

# Bad 循环内判断

blocks = []

while True:

block = f.read(32)

if block == '':

break

blocks.append(block)

# Better for语句中判断

blocks = []

for block in iter(partial(f.read, 32), ''):

blocks.append(block)

循环结束调用else

# Bad 在循环中创建标记

def find(seq, target):

found = False

for i, value in enumerate(seq):

if value == target:

found = True

break

if not found:

return -1

return i

# Better 通过for-else语句实现

def find(seq, target):

for i, value in enumerate(seq):

if value == target:

break

else:

return -1

return i

字典标记自增

colors = ['red', 'green', 'red', 'blue', 'green', 'red']

# Bad 判断字典是否存在key

d = {}

for color in colors:

if color not in d:

d[color] = 0

d[color] += 1

# Better 使用缺省值

d = {}

for color in colors:

d[color] = d.get(color, 0) + 1

# Best 使用 collections 包

d = collections.defaultdict(int)

for color in colors:

d[color] += 1

赋值

p = 'Raymond', 'Hettinger', 0x30, 'python@example.com'

# Bad 逐个赋值

fname = p[0]

lname = p[1]

age = p[2]

email = p[3]

# Better 统一赋值

fname, lname, age, email = p

# Bad 逐个赋值

def fibonacci(n):

x = 0

y = 1

for i in range(n):

print x

t = y

y = x + y

x = t

# Better 统一赋值

def fibonacci(n):

x, y = 0, 1

for i in range(n):

print x

x, y = y, x + y

字符串拼接

names = ['raymond', 'rachel', 'matthew', 'roger',

'betty', 'melissa', 'judith', 'charlie']

# Bad 使用“+”

s = names[0]

for name in names[1:]:

s += ', ' + name

print s

# Better 使用“join”

print ', '.join(names)

文件操作句柄处理

# Bad 使用try-finally

f = open('data.txt')

try:

data = f.read()

finally:

f.close()

# Better 使用 with

with open('data.txt') as f:

data = f.read()

lock = threading.Lock()

# Bad 使用try-finally

lock.acquire()

try:

print 'Critical section 1'

print 'Critical section 2'

finally:

lock.release()

# Better 使用 with

with lock:

print 'Critical section 1'

print 'Critical section 2'

忽略某个异常

# Bad 使用pass

try:

os.remove('somefile.tmp')

except OSError:

pass

# Better 使用ignored

with ignored(OSError):

os.remove('somefile.tmp’)

水平for条件

# Bad

result = []

for i in range(10):

s = i ** 2

result.append(s)

print sum(result)

# Better 语法糖

print sum(i**2 for i in xrange(10))

使用 % format 字符串

name = 'David'

messages = 3

text = ('Hello %s, you have %i messages'

% (name, messages))

以上,本文不定期更新~

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值