print会默认调用__str__方法吗

一、现象描述:

打印Mongodb自己生成的id:

print(res['_id'])
res['_id']

输出:
659faa6670433c2c86986861
ObjectId(‘659faa6670433c2c86986861’)

二、为什么会不一样呢

在 MongoDB 中,_id 字段通常是一个 ObjectId 类型的实例。当你在 Python 中打印一个 ObjectId 对象时,会自动调用该对象的 str() 方法,该方法返回对象的字符串表示形式。这就是为什么当你执行 print(res[‘_id’]) 时,你看到的是 ObjectId 的字符串形式,而不是 ObjectId 对象本身。

然而,当你在交互式解释器(如 Python shell 或 Jupyter notebook)中直接求值 res[‘_id’] 时,解释器会调用 repr() 方法,该方法返回一个可以被解释器重新解析的或者说“官方”的字符串表示。对于 ObjectId 类来说,repr() 方法返回的是 ObjectId(‘659faa6670433c2c86986861’) 这种形式,这个形式更准确地表明了这是一个 ObjectId 对象,而不是简单的字符串。

简而言之,两者之间的区别在于:

print(res[‘_id’]) 调用了 ObjectId 对象的 str() 方法,该方法返回了该 ObjectId 的字符串表示形式。
res[‘_id’] 在交互式环境中直接求值,调用了 ObjectId 对象的 repr() 方法,返回了一个明确表明对象类型的字符串表示。
这种区分在 Python 中是常见的,不仅适用于 ObjectId,还适用于许多其他对象。它有助于区分打印输出的友好显示和提供更多详细信息的官方字符串表示。

三、print会默认调用__str__方法吗

是的,在 Python 中,当你使用 print() 函数打印一个对象时,会默认调用该对象的 str() 方法来获取对象的字符串表示。这是因为 print() 需要一个可以显示的字符串来输出。

str() 方法的目的是返回一个对象的“非正式”或可打印的字符串表示,通常是为了可读性。这意味着它应该返回一个对终端用户友好的字符串。

如果一个对象没有定义 str() 方法,Python 会回退到使用 repr() 方法的返回值。repr() 方法的目标是返回一个对象的“正式”字符串表示,通常可以用来重新创建该对象。在开发中,它的输出通常是给开发者看的,而不是终端用户。

这里有一个简单的例子来说明这一点:

class Example1:
    def __repr__(self):
        return "Example.__repr__ called"

    def __str__(self):
        return "Example.__str__ called"
        
class Example2:
    def __repr__(self):
        return "Example.__repr__ called"
obj1 = Example1()
print(obj1)  # 会调用 __str__ 方法
obj2 = Example2()
print(obj2)  # 由于没有 __str__ 方法,会调用 __repr__ 方法

输出:
Example.str called
Example.repr called

四、结论:

这表明 print() 首选 str(),但如果没有定义 str(),它会使用 repr()。