代码之家  ›  专栏  ›  技术社区  ›  helpermethod

连接两个列表-“+=”和extend()之间的差异

  •  192
  • helpermethod  · 技术社区  · 16 年前

    一种方法是使用extend()方法:

    a = [1, 2]
    b = [2, 3]
    b.extend(a)
    

    另一个使用加号(+)运算符:

    b += a
    

    8 回复  |  直到 16 年前
        1
  •  243
  •   jesterjunk Michael Burr    11 年前

    .extend 方法涉及函数调用,在Python中,函数调用比 INPLACE_ADD

    这真的没什么好担心的,除非你做了几十亿次这个手术。然而,瓶颈可能会出现在其他地方。

        2
  •  196
  •   Donbeo    11 年前

    不能将+=用于非局部变量(函数的变量不是局部的,也不是全局的)

    def main():
        l = [1, 2, 3]
    
        def foo():
            l.extend([4])
    
        def boo():
            l += [5]
    
        foo()
        print l
        boo()  # this will fail
    
    main()
    

    这是因为 case编译器将加载变量 l LOAD_DEREF 指令,但for+=它将使用 LOAD_FAST -然后你得到 *UnboundLocalError: local variable 'l' referenced before assignment*

        3
  •  51
  •   isarandi    10 年前

    可以链接函数调用,但不能直接+=函数调用:

    class A:
        def __init__(self):
            self.listFoo = [1, 2]
            self.listBar = [3, 4]
    
        def get_list(self, which):
            if which == "Foo":
                return self.listFoo
            return self.listBar
    
    a = A()
    other_list = [5, 6]
    
    a.get_list("Foo").extend(other_list)
    a.get_list("Foo") += other_list  #SyntaxError: can't assign to function call
    
        4
  •  9
  •   Lance Ruo Zhang    9 年前

    我想说的是,当它与numpy(我刚才看到的问题是关于连接两个列表,而不是numpy数组,但因为它可能是一个问题,初学者,如我,我希望这可以帮助一些人谁寻求解决这个问题的帖子),例如。

    import numpy as np
    a = np.zeros((4,4,4))
    b = []
    b += a
    

    它将返回错误

    ValueError:操作数无法与形状(0,)(4,4,4)一起广播

    b.extend(a) 工作完美

        5
  •  5
  •   grofte    7 年前

    extend()适用于任何iterable*,+=适用于某些,但可能会变得很时髦。

    import numpy as np
    
    l = [2, 3, 4]
    t = (5, 6, 7)
    l += t
    l
    [2, 3, 4, 5, 6, 7]
    
    l = [2, 3, 4]
    t = np.array((5, 6, 7))
    l += t
    l
    array([ 7,  9, 11])
    
    l = [2, 3, 4]
    t = np.array((5, 6, 7))
    l.extend(t)
    l
    [2, 3, 4, 5, 6, 7]
    

    Python 3.6版

        6
  •  5
  •   Flux    6 年前

    从 CPython 3.5.2 source code :

    static PyObject *
    list_inplace_concat(PyListObject *self, PyObject *other)
    {
        PyObject *result;
    
        result = listextend(self, other);
        if (result == NULL)
            return result;
        Py_DECREF(result);
        Py_INCREF(self);
        return (PyObject *)self;
    }
    
        7
  •  3
  •   dalonsoa    7 年前

    ADD INPLACE_ADD 和 extend

    有了这些信息,我宁愿用 延伸 添加 在我看来,你所做的比 .

    请尝试以下代码几次(对于Python3):

    import time
    
    def test():
        x = list(range(10000000))
        y = list(range(10000000))
        z = list(range(10000000))
    
        # INPLACE_ADD
        t0 = time.process_time()
        z += x
        t_inplace_add = time.process_time() - t0
    
        # ADD
        t0 = time.process_time()
        w = x + y
        t_add = time.process_time() - t0
    
        # Extend
        t0 = time.process_time()
        x.extend(y)
        t_extend = time.process_time() - t0
    
        print('ADD {} s'.format(t_add))
        print('INPLACE_ADD {} s'.format(t_inplace_add))
        print('extend {} s'.format(t_extend))
        print()
    
    for i in range(10):
        test()
    
    ADD 0.3540440000000018 s
    INPLACE_ADD 0.10896000000000328 s
    extend 0.08370399999999734 s
    
    ADD 0.2024550000000005 s
    INPLACE_ADD 0.0972940000000051 s
    extend 0.09610200000000191 s
    
    ADD 0.1680199999999985 s
    INPLACE_ADD 0.08162199999999586 s
    extend 0.0815160000000077 s
    
    ADD 0.16708400000000267 s
    INPLACE_ADD 0.0797719999999913 s
    extend 0.0801490000000058 s
    
    ADD 0.1681250000000034 s
    INPLACE_ADD 0.08324399999999343 s
    extend 0.08062700000000689 s
    
    ADD 0.1707760000000036 s
    INPLACE_ADD 0.08071900000000198 s
    extend 0.09226200000000517 s
    
    ADD 0.1668420000000026 s
    INPLACE_ADD 0.08047300000001201 s
    extend 0.0848089999999928 s
    
    ADD 0.16659500000000094 s
    INPLACE_ADD 0.08019399999999166 s
    extend 0.07981599999999389 s
    
    ADD 0.1710910000000041 s
    INPLACE_ADD 0.0783479999999912 s
    extend 0.07987599999999873 s
    
    ADD 0.16435900000000458 s
    INPLACE_ADD 0.08131200000001115 s
    extend 0.0818660000000051 s
    
        8
  •  3
  •   Flux    6 年前

    这些信息碰巧被藏在 Programming FAQ

    ... 对于列表, __iadd__ [即。 += ]相当于打电话 extend += 是“速记”的意思 list.extend

    https://github.com/python/cpython/blob/v3.8.2/Objects/listobject.c#L1000-L1011

        9
  •  0
  •   Jann Poppinga    5 年前

    这会有用的

    t = ([],[])
    t[0].extend([1,2])
    

    t = ([],[])
    t[0] += [1,2]
    

    原因是 += 生成新对象。如果你看长版:

    t[0] = t[0] + [1,2]
    

    .extend() 修改元组中的对象,这是允许的。

        10
  •  -2
  •   littlebear333    8 年前

    根据Python进行数据分析。

    因此,

    everything = []
    for chunk in list_of_lists:
        everything.extend(chunk)
    

    比串联替代方案快:

    everything = []
    for chunk in list_of_lists:
        everything = everything + chunk
    

    enter image description here enter image description here