首页   注册   登录
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
拉勾
V2EX  ›  推广

在 Python 中, a += b 并不总是等价于 a = a + b

  •  
  •   itskingname · 51 天前 · 2628 次点击
    这是一个创建于 51 天前的主题,其中的信息可能已经有所发展或是发生改变。

    大家经常在一些博客中看到这样的说法:

    a += 1
    

    等价于

    a = a + 1
    

    这种说法实际上并不准确。

    我们来看一个例子:

    >>> a = [1, 2, 3]
    >>> a += (4,)
    >>> a
    [1, 2, 3, 4]
    
    >>> a = [1, 2, 3]
    >>> a = a + (4,)
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    TypeError: can only concatenate list (not "tuple") to list
    

    这里报错了,说明a += ba = a + b并不是完全等价的。

    请点击查看完整内容:在 Python 中,a += b 并不总是等价于 a = a + b

        1
    misaka19000   51 天前 via Android
    不错,学习了
        2
    OysterQAQ   51 天前 via iPhone
    学习了,查了下,在 java 中从本质讲这两者确实是两码事
        3
    sdijeenx   51 天前   ♥ 2
    是这样的。

    These methods are called to implement the augmented arithmetic assignments (+=, -=, *=, @=, /=, //=, %=, **=, <<=, >>=, &=, ^=, |=). These methods should attempt to do the operation in-place (modifying self) and return the result (which could be, but does not have to be, self). If a specific method is not defined, the augmented assignment falls back to the normal methods. For instance, if x is an instance of a class with an __iadd__() method, x += y is equivalent to x = x.__iadd__(y) . Otherwise, x.__add__(y) and y.__radd__(x) are considered, as with the evaluation of x + y. In certain situations, augmented assignment can result in unexpected errors (see Why does a_tuple[i] += [‘ item ’] raise an exception when the addition works?), but this behavior is in fact part of the data model.
    https://docs.python.org/3/reference/datamodel.html


    Why does a_tuple[i] += [‘ item ’] raise an exception when the addition works?
    This is because of a combination of the fact that augmented assignment operators are assignment operators, and the difference between mutable and immutable objects in Python.

    This discussion applies in general when augmented assignment operators are applied to elements of a tuple that point to mutable objects, but we ’ ll use a list and += as our exemplar.
    https://docs.python.org/3/faq/programming.html#faq-augmented-assignment-tuple-error
        4
    rekulas   51 天前
    这个,我觉得别人说的是数值吧,你这个改成了 dict 相加不符合别人的原意了?(非 python 研究者,这似乎是 dict 吧)
        5
    bumz   51 天前
    本来就不是一回事

    只不过对于值语义的类型,这二者的结果期望是等价的

    list 是引用语义的类型,不等价
        6
    whwq2012   51 天前 via Android
    偷换概念。。一般说的+=是数字运算,又不是其他对象。。
        7
    helloworld000   51 天前   ♥ 12
    现在从 python 开始学编程的人都已经不知道 数据类型这么个东西了吗。。。。
        8
    mario85   51 天前 via iPhone   ♥ 3
    推公众号的吧。
    @Livid
        9
    itskingname   51 天前 via iPhone
    @mario85 已 block
        10
    pkookp8   51 天前 via Android
    这算是运算符重载吧
    你想写成什么样都可以
        11
    lance6716   51 天前 via Android   ♥ 11
    @itskingname 竟然还反向 b,牛逼牛逼
        12
    junmoxiao   51 天前 via Android
    ,,,,,这,,,水平有点低呀
        13
    ETiV   51 天前 via iPhone
    大家还是拒绝服务攻击吧
        14
    leido   51 天前 via Android
    这是运算符重载,楼主偷换概念
        15
    Trumeet   51 天前 via Android
    数据类型 数据类型
        16
    master13   51 天前   ♥ 6
    那按照楼主这逻辑,a+b=b+a 也不准确,当 a 和 b 都是 str 的时候……

    玩这个有意思吗
        17
    Qzier   51 天前 via iPhone
    废话,+ 对应的是 __add__ 方法,+= 对应的是 __iadd__ 或 __iconcat__ 方法,当然不同,完全取决于你的实现!
        18
    Qzier   51 天前 via iPhone
    补充下 + 对应的方法还有 __concat__,是针对序列类型的
        19
    xiri   51 天前 via Android
    这是 python 里面特殊的运算符重载吧,一般说的+=是针对数值运算的。按楼主这样描述,我自己重定义一下,还可以实现其他功能呢
        20
    fan123199   51 天前
    介绍知识点不错,但不要搞个大新闻(常指标题浮夸),因为这个知识点很可能是常识。
        21
    mayne95   51 天前 via Android
    大家都知道🐱和🐶生不出🐱
        22
    cpyhaha   51 天前 via Android
    感觉楼主的出发点还是没错的,但是这种问题一般会比较针对初学者吧!来 V2 就挨喷了
        23
    Mirage09   51 天前   ♥ 1
    V2EX 该出个 newbie 节点,把这些东西放在这个节点。
        24
    omri   51 天前
    学习了,感谢楼主
        25
    msg7086   51 天前
    += 和 + 本来就是两个运算符。通常为了不反直觉,都尽量把他们定义成一样的意思。
    你要是喜欢,还能把+定义成-呢。
    以前不是还有人把 true 和 false 的定义对调着玩吗?你是不是又要说 true 等价于 false 呢。
        26
    tabris17   51 天前
    a += 1
    应该等价于
    a = a + 1

    如果不等价,那就是实现上有问题,属于副作用
        27
    Livid   V2EX Moderator   51 天前
    @Mirage09 谢谢。我们有这个节点:

    /go/newbie
        28
    Livid   V2EX Moderator   51 天前
    @itskingname 营销内容只能发到这个节点:

    /go/promotions

    这个主题已经被移动。
        29
    Mirage09   51 天前 via iPhone
    @Livid 还真的有😂疏忽了
        30
    itskingname   51 天前
    @Livid 感谢站长提醒。不过这篇文章我确实没有推销东西啊。博客上面的二维码是每篇文章自动添加的。
    关于   ·   FAQ   ·   API   ·   我们的愿景   ·   广告投放   ·   感谢   ·   实用小工具   ·   2475 人在线   最高记录 4385   ·  
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.3 · 18ms · UTC 11:52 · PVG 19:52 · LAX 04:52 · JFK 07:52
    ♥ Do have faith in what you're doing.
    沪ICP备16043287号-1