1.__repr__函数 函数str()用于将值转化为适于人阅读的形式,而repr()转化为供解释器读取的形式,某对象没有适于人阅读的解释形式的话,str()会返回与repr(),所以print展示的都是str的格式。 我们经常会直接输出类的实例化对象,例如: class CLanguage: pass clangs = CLanguage() print(clangs) 程序运行结果为: < __main__.CLanguage object at 0x000001A7275221D0 > 通常情况下,直接输出某个实例化对象,本意往往是想了解该对象的基本信息,例如该对象有哪些属性,它们的值各是多少等等。但默认情况下,我们得到的信息只会是“类名 + object at + 内存地址”,对我们了解该实例化对象帮助不大。 那么,有没有可能自定义输出实例化对象时的信息呢?答案是肯定,通过重写类的__repr__()方法即可。事实上,当我们输出某个实例化对象时,其调用的就是该对象的__repr__()方法,输出的是该方法的返回值。 以本节开头的程序为例,执行print(clangs)等同于执行print(clangs.__repr__()),程序的输出结果是一样的(输出的内存地址可能不同)。 和__init__(self)的性质一样,Python中的每个类都包含__repr__()方法,因为object类包含__reper__()方法,而Python中所有的类都直接或间接继承自object类。 默认情况下,__repr__()会返回和调用者有关的 “类名 + object at + 内存地址”信息。当然,我们还可以通过在类中重写这个方法,从而实现当输出实例化对象时,输出我们想要的信息。 举个例子: class CLanguage: def __init__(self): self.name = "abc" self.add = "123" def __repr__(self): return "CLanguage[name=" + self.name + ",add=" + self.add + "]" clangs = CLanguage() print(clangs) 程序运行结果为: CLanguage[name = abc, add = 123] 由此可见,__repr__()方法是类的实例化对象用来做“自我介绍”的方法,默认情况下,它会返回当前对象的“类名 + object at + 内存地址”,而如果对该方法进行重写,可以为其制作自定义的自我描述信息。 2.__str__() 直接打印对象的实现方法,__str__是被print函数调用的。打印一个实例化对象时,打印的其实时一个对象的地址。而通过__str__()函数就可以帮助我们打印对象中具体的属性值,或者你想得到的东西。 在Python中调用print()打印实例化对象时会调用__str__()。如果__str__()中有返回值,就会打印其中的返回值。 class Cat: """定义一个猫类""" def __init__(self, new_name="汤姆", new_age=20): """在创建完对象之后 会自动调用, 它完成对象的初始化的功能""" self.name = new_name self.age = new_age # 它是一个对象中的属性,在对象中存储,即只要这个对象还存在,那么这个变量就可以使用 # num = 100 # 它是一个局部变量,当这个函数执行完之后,这个变量的空间就没有了,因此其他方法不能使用这个变量 def __str__(self): """返回一个对象的描述信息""" # print(num) return "名字是:%s , 年龄是:%d" % (self.name, self.age) # 创建了一个对象 tom = Cat("汤姆", 30) print(tom) 输出结果: 名字是: 汤姆, 年龄是: 30 总结:当使用print输出对象的时候,只要自己定义了__str__(self)方法,那么就会打印从在这个方法中return的数据。__str__方法需要返回一个字符串,当做这个对象的描写。 3.__repr__和__str__区别 看下面的例子就明白了: class Test(object): def __init__(self, value='hello, world!'): self.data = value >> > t = Test() >> > t < __main__.Test at 0x7fa91c307190 > >> > print(t) < __main__.Test object at 0x7fa91c307190 > # 看到了么?上面打印类对象并不是很友好,显示的是对象的内存地址 # 下面我们重构下该类的__repr__以及__str__,看看它们俩有啥区别 # 重构__repr__ class TestRepr(Test): def __repr__(self): return 'TestRepr(%s)' % self.data >> > tr = TestRepr() >> > tr 直接终端显示,不print就是面向程序员 TestRepr(hello, world!) >> > print(tr) print是面向程序员 TestRepr(hello, world!) # 重构__repr__方法后,不管直接输出对象还是通过print打印的信息都按我们__repr__方法中定义的格式进行显示了 # 重构__str__ calss TestStr(Test): def __str__(self): return '[Value: %s]' % self.data >> > ts = TestStr() >> > ts < __main__.TestStr at 0x7fa91c314e50 > >> > print(ts) [Value: hello, world!] # 你会发现,直接输出对象ts时并没有按我们__str__方法中定义的格式进行输出,而用print输出的信息却改变了 __repr__和__str__这两个方法都是用于显示的,__str__是面向用户的,而__repr__面向程序员。 打印操作会首先尝试__str__和str内置函数(print运行的内部等价形式),它通常应该返回一个友好的显示。 __repr__用于所有其他的环境中:用于交互模式下提示回应以及repr函数,如果没有使用__str__,会使用print和str。它通常应该返回一个编码字符串,可以用来重新创建对象,或者给开发者详细的显示。 当我们想所有环境下都统一显示的话,可以重构__repr__方法;当我们想在不同环境下支持不同的显示,例如终端用户显示使用__str__,而程序员在开发期间则使用底层的__repr__来显示,实际上__str__只是覆盖了__repr__以得到更友好的用户显示。