Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/list/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python:将iterable转换为list:';列表(x)和#x27;与全切片相比';x[:]和#x27;_Python_List_Slice - Fatal编程技术网

Python:将iterable转换为list:';列表(x)和#x27;与全切片相比';x[:]和#x27;

Python:将iterable转换为list:';列表(x)和#x27;与全切片相比';x[:]和#x27;,python,list,slice,Python,List,Slice,我想知道在Python中将iterable转换为list的这两种方法是否有任何区别: 使用list()构造函数: my_list = list(my_iterable) 使用完整切片: my_list = my_iterable[:] 在实施过程中是否存在差异?如果是,性能如何?Python2和Python3之间有什么变化吗 当然,我意识到构造函数版本的可读性更好。list(thing)提供了一个列表 thing[:]可以给你它想要的任何类型 换句话说,第二个选项只适用于特定类型(您

我想知道在Python中将iterable转换为list的这两种方法是否有任何区别:

  • 使用
    list()
    构造函数:

    my_list = list(my_iterable)
    
  • 使用完整切片:

    my_list = my_iterable[:]
    
在实施过程中是否存在差异?如果是,性能如何?Python2和Python3之间有什么变化吗

当然,我意识到构造函数版本的可读性更好。

list(thing)
提供了一个列表

thing[:]
可以给你它想要的任何类型

换句话说,第二个选项只适用于特定类型(您没有提到实际使用的类型)

编辑:
thing[:]
的一个有用特性是,当它被支持时,通常会导致引用“thing的所有元素”,可以在不更改对象
thing
指向的情况下对其进行修改。例如:

thing[:] = [1,2,3]
[1,2,3]
分配到
内容
的上方,即使这本身不是一个列表。鉴于:

list(thing) = [1,2,3]
这是胡说八道,而且:

thing = [1,2,3]

使
事物
引用新列表,而不管其以前的类型。

并非所有事物都支持切片,例如生成器:

(x for x in range(5))[:]   # raises an error
因此,
列表
更一般
[:]
是一种复制列表的方法

之所以可以使用
[:]
,主要原因是当您将冒号前的索引省略(例如
[:3]
)和冒号后的索引省略组合在一起时,这两种方法都很有用。如果添加一个步骤也很有用,例如,
[::-1]
是反转字符串的常用方法<代码>[:]本身对列表不是很有用,但在某些情况下它会稍微快一点,正如我对Padriac答案的评论,尽管可读性通常比这种微观优化更重要

对于非列表,
[:]
理论上可以根据您告诉它的内容执行任何操作:

class A(object):
    def __getitem__(self, item):
        return 3

print A()[:]  # prints 3
但是您可能应该避免这样的定义。

我认为我的iterable始终是一个列表或列表的子类,或者这两种方法可能产生完全不同的结果:

在python2中,调用列表比切片稍快:

In [2]: l = list(range(1000000))

In [3]: timeit l[:]
100 loops, best of 3: 10.8 ms per loop

In [4]: timeit list(l)
100 loops, best of 3: 9.45 ms per loop
Python3的结果非常相似:

In [1]: l = list(range(1000000))

In [2]: timeit list(l)
100 loops, best of 3: 9.54 ms per loop

In [3]: timeit l[:]
100 loops, best of 3: 10.6 ms per loop
[:]
用于从任何支持切片的元素中切片所有元素,尝试比较调用
list
或使用
[:]
时,如果
my_iterable
是一个列表,则没有实际意义,因为它们都会根据您使用它们的内容执行非常不同的操作

In [2]: i = (1,2,3,4,5)

In [3]: list(i)
Out[3]: [1, 2, 3, 4, 5]

In [4]: i[:]
Out[4]: (1, 2, 3, 4, 5)

In [5]: i = "hello world"

In [6]: list(i)
Out[6]: ['h', 'e', 'l', 'l', 'o', ' ', 'w', 'o', 'r', 'l', 'd']

In [7]: i[:]
Out[7]: 'hello world'

我通常总是使用
list(thing)
,完整的片段只是我偶尔在CodeGolf上看到的。因此,我实际上并不知道切片操作符只对有限的iterables子集起作用。感谢您的课程,我将继续并一如既往地使用
list(thing)
。但是真的需要完整的切片操作符吗?调用
list(my_list)
也会创建一个具有不同
id
@ByteCommander的新实例:
[:]
在现实世界中的主要用途是将列表或数组的所有元素指定到位。例如,
x=[1,2,3];x=[4,5,6]
x
创建了一个完全不同的对象,以便第二次引用。但是
x=[1,2,3];x[:]=[4,5,6]
使
x
引用同一列表对象,并覆盖内容。例如,这在NumPy中经常很有用。我更新了我的答案来反映其中的一些。哦,酷!我还没听说过分配一个切片。感谢您的这些见解。那么是否真的需要完整的切片操作符
[:]
?调用
list(my_list)
也会创建一个具有不同
id
的新实例,这与切片的行为相同。如果将开始更改为
range(10)
,则结果会颠倒
[:]
避免查找名称
列表
,因此,如果您必须复制多个小列表,则会更快。