|
马上注册,结交更多好友,享用更多功能^_^
您需要 登录 才可以下载或查看,没有账号?立即注册
x
关于__new__()这个魔法方法,小甲鱼在书中写道
‘就是当继承一个不可变的类型的时候,它的特性就显得尤为重要了’
举出例子:
class CapeStr(str):
def __new__(cls, string):
string = string.upper()
return str.__new__(cls, string)
a = CapeStr('I love FishC.com')
a
'I LOVE FISHC.COM'
我在询问AI 时,它告诉我:无论是在__new__()方法中还是在__init__()方法中修改不可变对象的值,都只会创建一个新的对象并返回,而不会改变原对象的值。要修改不可变对象的值,需要创建一个新的对象并重新赋值。
我的理解是 __new__() 在对象实例化的同时赋值string这个属性并大写处理,那么这让我联想到 __init__() 也是这样做的呀
我是不是可以这样:
class Capestr_new:
def __init__(self, string):
self.string = string.upper()
c = Capestr_new('I love FishC.com')
c.string
'I LOVE FISHC.COM'
如果都是创建新的对象,那么 __new__()对不可变对象修改的优势在哪里?
我知道我对 __new__()的看法是有问题的, 这是我不能继续学下去的原因,这里把我弄糊涂了,希望有大佬帮我解惑?
本帖最后由 歌者文明清理员 于 2024-2-24 16:09 编辑
Python 变量分为可变和不可变。
首先了解 Python 的对象储存机制:
举例:
这样其实是在 "str"(字符串)上面贴了一个 a(变量名),然后把 "str" 上的 a 扔了,把 a 贴到 "str" + "ing" ("string") 上了。
也就是说创建了一个新的字符串。str 是不可变量
这就不一样了:创建 [](列表),然后贴上 a,再在 [] 里塞进去一个 1。
所以这是同一个列表。list 是不可变量
__new__ 的用法如下:
class MyString(str):
def __new__(cls, string):
print("new")
self = super().__new__(cls, string) # 这一步其实调用了父类 str 的方法
return self
def __init__(self, string):
print("init")
看看上面的代码,再在终端里运行下,就懂了。
new 的优势(更正):在使用不可变量作为父类时,使用 new 会调用父类的方法生成 self。这避免了 str 的子类(应该是不可变量)变成可变的,从而引发 bug。
|
|