Python编码模式

Python 编码模式

新建文件模板

#!/usr/bin/env python
# -*- coding: utf-8 -*-

README.md

简述系统内容,可以使用markdown语法自定义格式

重设系统编码

import sys

try:
reload(sys)
    sys.setdefaultencoding('utf-8')
except NameError:
    # The only supported default encodings in Python are:

    #  Python 2.x: ASCII
    #  Python 3.x: UTF-8
    # So no need to sys.setdefaultencoding('utf-8')
    pass # py3

log设置与使用

  1. logging.conf 配置命令行和文件的日志读写
[loggers]
keys=root,kol

[handlers]
keys=consoleHandler,fileHandler

[formatters]
keys=simpleFormatter

[logger_root]
level=DEBUG
handlers=consoleHandler

[logger_kol]
level=DEBUG
handlers=consoleHandler,fileHandler
qualname=kol
propagate=0

[handler_consoleHandler]
class=StreamHandler
level=DEBUG
formatter=simpleFormatter
args=(sys.stdout,)

[handler_fileHandler]  
class=logging.handlers.RotatingFileHandler  
level=DEBUG  
formatter=simpleFormatter  
args=('kol.log','a',20000,5,)

[formatter_simpleFormatter]
format=%(asctime)s - %(name)s - %(levelname)s - %(message)s
datefmt=
  1. __init__.py 初始化logger
import logging.config

logging.config.fileConfig("logging.conf")
logger = logging.getLogger(\__name__)
logger.debug("started logging %s." % \__name__)
  1. .gitignore 在项目中排除log文件
# project
*.log

config使用

import ConfigParser

config = ConfigParser.ConfigParser()
config.read("d:/influence.conf")
username = config.get("weibo", "username")
password = config.get("weibo", "password")

缓存的使用

python3自带,python2下使用lru_cache_function

import lru

cookies = [000, 111, 222, 333, 444]


@lru.lru_cache_function(max_size=1024, expiration=15 * 60)
def f(account):
    print "Calling f(" + str(account) + ")"
    return cookies[account]

    print f(3)
    print f(0)
    print f(3)  # 15分钟内有效

异常的使用

import traceback

try:
    raise IOError("io error!!!")  # 抛出第一个异常,被except捕获了    
except IOError, io_error:
    traceback.print_exc()   # 打印异常栈,第一个异常的栈
    print sys.exc_info()    # 打印异常信息
    print io_error          # 打印异常消息
    pass  # 异常处理完毕,系统正常继续
finally:
    print "1 print always..."

try:
    raise IOError("io error!!!")  # 抛出第一个异常,被except捕获了
except IOError, io_error:
    raise IOError("raise io error!!!")  # 抛出第二个异常,会被系统捕获,系统退出
finally:
    print "2 print always..."  # 但是还是会运行这里

注意:异常中不要使用裸露的except,except后跟具体的exceptions

异常和日志的组合

python编译时能检查的问题相对较少
except 一定要打印 & 出WARN/ERROR的log

语法杂项

1.使用random choice随机选取seq一个值

import random

print random.choice((1, 2, 3))
print random.choice(['3', '4', 12L])

2.使用sum代替连加的reduce

新建文件test_sum.py,使用py.test测试验证结果

#!/usr/bin/env python
# -*- coding: utf-8 -*-


def test_sum():
assert sum([1, 2, 3], 0) == 6
assert reduce(lambda a, b: a + b, [1, 2, 3], 0) == 6
F:\gitlab\mola\house\learnpy>py.test
============================= test session starts =============================
platform win32 -- Python 2.7.11, pytest-2.8.5, py-1.4.31, pluggy-0.3.1
rootdir: F:\gitlab\mola\house\learnpy, inifile:
collected 1 items

test_sum.py .

========================== 1 passed in 0.01 seconds ===========================

3.使用with处理文件连接(类似java7的自动关闭try)
4.json编码存文件(注意两段的区别):

person = {"name": "哈哈哈"}
with open(file_name, "a") as f:
    f.write(json.dumps(person, ensure_ascii=False) + "\n")

person = {"name": u"哈哈哈"}
with codecs.open(file_name, "a", "utf-8") as f:
    f.write(json.dumps(person, ensure_ascii=False) + "\n")
  1. 使用startswith() and endswith()代替切片进行序列前缀或后缀的检查。比如:
    • Yes: if foo.startswith('bar'):优于
    • No: if foo[:3] == 'bar':
  2. 使用isinstance()比较对象的类型。比如
    Yes: if isinstance(obj, int): 优于
    No: if type(obj) is type(1):
  3. 判断序列空或不空,有如下规则
    Yes: if not seq:
    if seq:
    优于
    No: if len(seq)
    if not len(seq)
  4. 二进制数据判断使用 if boolvalue的方式。

docstring

模块/类/函数下的第一个字符串,作为文档存在
可使用help()或者__doc__访问
其间可以夹杂doctest作为简单的测试(较复杂的测试可以使用unittest或者功能强大但更简洁的py.test

doctest

新建hello_doctest.py,使用doctest验证其作用:

#!/usr/bin/env python
# -*- coding: utf-8 -*-

"""
This is the "example" module.

The example module supplies one function, factorial().  For example,

>>> factorial(5)
120
"""


def factorial(n):
"""Return the factorial of n, an exact integer >= 0.

    If the result is small enough to fit in an int, return an int.
    Else return a long.

    >>> [factorial(n) for n in range(6)]
    [1, 1, 2, 6, 24, 120]
    >>> [factorial(long(n)) for n in range(6)]
    [1, 1, 2, 6, 24, 120]
    >>> factorial(30)
    265252859812191058636308480000000L
    >>> factorial(30L)
    265252859812191058636308480000000L
    >>> factorial(-1)
    Traceback (most recent call last):
        ...
    ValueError: n must be >= 0

    Factorials of floats are OK, but the float must be an exact integer:
    >>> factorial(30.1)
    Traceback (most recent call last):
        ...
    ValueError: n must be exact integer
    >>> factorial(30.0)
    265252859812191058636308480000000L

    It must also not be ridiculously large:
    >>> factorial(1e100)
    Traceback (most recent call last):
        ...
    OverflowError: n too large
    """

import math
if not n >= 0:
raise ValueError("n must be >= 0")
if math.floor(n) != n:
raise ValueError("n must be exact integer")
if n + 1 == n:  # catch a value like 1e300
raise OverflowError("n too large")
    result = 1
factor = 2
while factor <= n:
        result *= factor
        factor += 1
return result


if __name__ == "__main__":
import doctest
    doctest.testmod()

F:\gitlab\mola\house\learnpy>python hello_doctest.py -v

Trying:
    factorial(5)
Expecting:
    120
ok
Trying:
    [factorial(n) for n in range(6)]
Expecting:
    [1, 1, 2, 6, 24, 120]
ok
Trying:
    [factorial(long(n)) for n in range(6)]
Expecting:
    [1, 1, 2, 6, 24, 120]
ok
Trying:
    factorial(30)
Expecting:
    265252859812191058636308480000000L
ok
Trying:
    factorial(30L)
Expecting:
    265252859812191058636308480000000L
ok
Trying:
    factorial(-1)
Expecting:
    Traceback (most recent call last):
        ...
    ValueError: n must be >= 0
ok
Trying:
    factorial(30.1)
Expecting:
    Traceback (most recent call last):
        ...
    ValueError: n must be exact integer
ok
Trying:
    factorial(30.0)
Expecting:
    265252859812191058636308480000000L
ok
Trying:
    factorial(1e100)
Expecting:
    Traceback (most recent call last):
        ...
    OverflowError: n too large
ok
2 items passed all tests:
   1 tests in __main__
   8 tests in __main__.factorial
9 tests in 2 items.
9 passed and 0 failed.
Test passed.

注意:在测试通过的情况下,默认不打印详情。加上-v参数可以查看测试的详情。

样式:PEP8

PEP8全文见:https://www.python.org/dev/peps/pep-0008/

自动检测: autopep8

安装:pip install autopep8

关键点如下:
1. 模块内容的顺序
模块说明和docstring—import—globals&constants—其他定义。其中import部分,又按标准、三方和自己编写顺序依次排放,之间空一行。

  1. 不要在一句import中多个库,比如import os, sys不推荐。

  2. 如果采用from XX import XX引用库,可以省略‘module.’,都是可能出现命名冲突,这时就要采用import XX。

  3. 模块命名尽量短小,使用全部小写的方式,可以使用下划线。

  4. 包命名尽量短小,使用全部小写的方式,不可以使用下划线。

  5. 类的命名使用CapWords的方式,模块内部使用的类采用_CapWords的方式。

  6. 异常命名使用CapWords+Error后缀的方式。

  7. 函数命名使用全部小写的方式,可以使用下划线。

  8. 常量命名使用全部大写的方式,可以使用下划线。

  9. 类的属性(方法和变量)命名使用全部小写的方式,可以使用下划线。
    类的属性有3种作用域public、non-public和subclass API,可以理解成C++中的public、private、protected,non-public属性前,前缀一条下划线。
    类的属性若与关键字名字冲突,后缀一下划线,尽量不要使用缩略等其他方式。

11.其他:
- 有语义分隔的加空行
- 标点符号后加空格
- 长行加\分行,运算符置于下行头部

import this:Python 之禅

  • Beautiful is better than ugly.
    优美胜于丑陋。

  • Explicit is better than implicit.
    显式胜于隐式。

  • Simple is better than complex.
    简单胜于复杂。

  • Complex is better than complicated.
    复杂胜于难懂。

  • Flat is better than nested.
    扁平胜于嵌套。

  • Sparse is better than dense.
    分散胜于密集。

  • Readability counts.
    可读性应当被重视。

  • Special cases aren’t special enough to break the rules. Although practicality beats purity.
    尽管实用性会打败纯粹性,特例也不能凌驾于规则之上。

  • Errors should never pass silently. Unless explicitly silenced.
    除非明确地使其沉默,错误永远不应该默默地溜走。

  • In the face of ambiguity, refuse the temptation to guess.
    面对不明确的定义,拒绝猜测的诱惑。

  • There should be one– and preferably only one –obvious way to do it.
    用一种方法,最好只有一种方法来做一件事。

  • Although that way way not be obvious at first unless you’re Dutch.
    虽然一开始这种方法并不是显而易见的,但谁叫你不是Python之父呢。

  • Now is better than never. Although never is often better than right now.
    做比不做好,但立马去做有时还不如不做。

  • If the implementation is hard to explain, it’s a bad idea.
    如果实现很难说明,那它是个坏想法。

  • If the implementation is easy to explain, it may be a good idea.
    如果实现容易解释,那它有可能是个好想法。

  • Namespaces are one honking great idea – let’s do more of those!
    命名空间是个绝妙的想法,让我们多多地使用它们吧!


版权声明:转载必须注明本文转自 East196 的博客:http://blog.csdn.net/east196

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

AI原吾

你的鼓励是我创作最大的动力~

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值