# 8.12. `reprlib` - 替代`repr()`实现

源代码： Lib/reprlib.py

`reprlib` 模块提供了手段，为生产对象交涉的结果字符串的大小限制。这用在 Python 调试器中和在其他上下文可能很有用。

本模块提供了一个类、 实例和一个函数︰

class `reprlib.``Repr`

  类提供格式化服务有用在执行功能类似于内置 `repr()`;为避免过长的意见书的代添加不同的对象类型的大小限制。

`reprlib.``aRepr`

  这是 `repr` 用来提供如下所述的 `repr()` 函数的一个实例。更改此对象的属性将影响由 `repr()` 和 Python 调试器使用的大小限制。

`reprlib.``repr`(obj)

  这是`aRepr`的`repr()`方法。它返回一个类似于由同名内建函数返回的字符串，但对大多数大小有限制。

除了大小限制工具，模块还提供了装饰器，用于检测对`__repr__()`的递归调用，并替换为占位符字符串。

`@``reprlib.``recursive_repr`(fillvalue="...")

  装饰器用于检测同一线程中的递归调用的`__repr__()`方法。如果进行了递归调用，则会返回fillvalue，否则，将执行通常的`__repr__()`调用。例如：

      >>> class MyList(list):
      ...     @recursive_repr()
      ...     def __repr__(self):
      ...         return '<' + '|'.join(map(repr, self)) + '>'
      ...
      >>> m = MyList('abc')
      >>> m.append(m)
      >>> m.append('x')
      >>> print(m)
      <'a'|'b'|'c'|...|'x'>

  版本3.2中的新功能。

## 8.12.1.Repr对象

`Repr`实例提供了几个属性，可用于为不同对象类型的表示提供大小限制，以及格式化特定对象类型的方法。

`Repr.``maxlevel`

  创建递归表示的深度限制。默认值为`6`。

`Repr.``maxdict`
`Repr.``maxlist`
`Repr.``maxtuple`
`Repr.``maxset`
`Repr.``maxfrozenset`
`Repr.``maxdeque`
`Repr.``maxarray`

  对指定对象类型表示的条目数的限制。对于`maxdict`，`5`的`maxarray`和`6`，默认值为`4`其他。

`Repr.``maxlong`

  整数的表示中的最大字符数。数字从中间掉落。默认值为`40`。

`Repr.``maxstring`

  限制字符串表示中的字符数。注意，字符串的“正常”表示被用作字符源：如果在表示中需要转义序列，当表示被缩短时，这些可能被破坏。默认值为`30`。

`Repr.``maxother`

  此限制用于控制在`Repr`对象上没有可用的特定格式化方法的对象类型的大小。它以与`maxstring`类似的方式应用。默认值为`20`。

`Repr.``repr`(obj)

  相当于内建`repr()`，它使用实例强加的格式。

`Repr.``repr1`(obj, level)

  `repr()`使用递归实现。这使用obj类型来确定要调用的格式化方法，将其传递obj和级别。The type-specific methods should call `repr1()` to perform recursive formatting, with `level - 1` for the value of level in the recursive call.

`Repr.``repr_TYPE`(obj, level)

  特定类型的格式化方法实现为基于类型名称的名称的方法。在方法名称中，TYPE被替换为`'_'.join(type(obj).__name__.split())`。对这些方法的调度由`repr1()`处理。需要递归格式化值的类型特定方法应调用`self.repr1（subobj， level - 1）` 。

## 8.12.2.子类Repr对象

通过`Repr.repr1()`使用动态分发允许`Repr`的子类添加对其他内建对象类型的支持或修改已支持类型的处理。此示例显示如何添加对文件对象的特殊支持：

    import reprlib
    import sys

    class MyRepr(reprlib.Repr):

        def repr_TextIOWrapper(self, obj, level):
            if obj.name in {'<stdin>', '<stdout>', '<stderr>'}:
                return obj.name
            return repr(obj)

    aRepr = MyRepr()
    print(aRepr.repr(sys.stdin))         # prints '<stdin>'