Python编程语言中有哪些鲜为人知但很有用的特性?

尽量将答案限制在Python核心。 每个回答一个特征。 给出一个例子和功能的简短描述,而不仅仅是文档链接。 使用标题作为第一行标记该特性。

快速链接到答案:

参数解包 牙套 链接比较运算符 修饰符 可变默认参数的陷阱/危险 描述符 字典默认的.get值 所以测试 省略切片语法 枚举 其他/ 函数作为iter()参数 生成器表达式 导入该 就地值交换 步进列表 __missing__物品 多行正则表达式 命名字符串格式化 嵌套的列表/生成器推导 运行时的新类型 .pth文件 ROT13编码 正则表达式调试 发送到发电机 交互式解释器中的制表符补全 三元表达式 试着/ / else除外 拆包+打印()函数 与声明


当前回答

每次打印一屏多行字符串

没有真正有用的功能隐藏在网站。_Printer类,其license对象是一个实例。调用后者时,打印Python许可证。可以创建另一个相同类型的对象,传递一个字符串——例如文件的内容——作为第二个参数,并调用它:

type(license)(0,open('textfile.txt').read(),0)()

这将打印一次按一定行数分割的文件内容:

...
file row 21
file row 22
file row 23

Hit Return for more, or q (and Return) to quit:

其他回答

分配和删除切片:

>>> a = range(10)
>>> a
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> a[:5] = [42]
>>> a
[42, 5, 6, 7, 8, 9]
>>> a[:1] = range(5)
>>> a
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> del a[::2]
>>> a
[1, 3, 5, 7, 9]
>>> a[::2] = a[::-2]
>>> a
[9, 3, 5, 7, 1]

注意:当赋值给扩展片(s[start:stop:step])时,赋值的可迭代对象必须与片的长度相同。

列表中的无限递归

>>> a = [1,2]
>>> a.append(a)
>>> a
[1, 2, [...]]
>>> a[2]
[1, 2, [...]]
>>> a[2][2][2][2][2][2][2][2][2] == a
True

切片运算符中的step参数。例如:

a = [1,2,3,4,5]
>>> a[::2]  # iterate over the whole list in 2-increments
[1,3,5]

特殊情况x[::-1]是“x反转”的有用习语。

>>> a[::-1]
[5,4,3,2,1]

可读正则表达式

在Python中,您可以将正则表达式拆分为多行,命名匹配并插入注释。

示例详细语法(来自Python):

>>> pattern = """
... ^                   # beginning of string
... M{0,4}              # thousands - 0 to 4 M's
... (CM|CD|D?C{0,3})    # hundreds - 900 (CM), 400 (CD), 0-300 (0 to 3 C's),
...                     #            or 500-800 (D, followed by 0 to 3 C's)
... (XC|XL|L?X{0,3})    # tens - 90 (XC), 40 (XL), 0-30 (0 to 3 X's),
...                     #        or 50-80 (L, followed by 0 to 3 X's)
... (IX|IV|V?I{0,3})    # ones - 9 (IX), 4 (IV), 0-3 (0 to 3 I's),
...                     #        or 5-8 (V, followed by 0 to 3 I's)
... $                   # end of string
... """
>>> re.search(pattern, 'M', re.VERBOSE)

命名匹配示例(摘自正则表达式HOWTO)

>>> p = re.compile(r'(?P<word>\b\w+\b)')
>>> m = p.search( '(((( Lots of punctuation )))' )
>>> m.group('word')
'Lots'

由于字符串字面值的串联,你也可以在不使用re.VERBOSE的情况下详细地编写一个正则表达式。

>>> pattern = (
...     "^"                 # beginning of string
...     "M{0,4}"            # thousands - 0 to 4 M's
...     "(CM|CD|D?C{0,3})"  # hundreds - 900 (CM), 400 (CD), 0-300 (0 to 3 C's),
...                         #            or 500-800 (D, followed by 0 to 3 C's)
...     "(XC|XL|L?X{0,3})"  # tens - 90 (XC), 40 (XL), 0-30 (0 to 3 X's),
...                         #        or 50-80 (L, followed by 0 to 3 X's)
...     "(IX|IV|V?I{0,3})"  # ones - 9 (IX), 4 (IV), 0-3 (0 to 3 I's),
...                         #        or 5-8 (V, followed by 0 to 3 I's)
...     "$"                 # end of string
... )
>>> print pattern
"^M{0,4}(CM|CD|D?C{0,3})(XC|XL|L?X{0,3})(IX|IV|V?I{0,3})$"

Doctest:同时进行文档和单元测试。

从Python文档中提取的示例:

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(-1)
    Traceback (most recent call last):
        ...
    ValueError: n must be >= 0

    Factorials of floats are OK, but the float must be an exact integer:
    """

    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

def _test():
    import doctest
    doctest.testmod()    

if __name__ == "__main__":
    _test()