Python 3将范围转换为列表


178

我正在尝试列出其中的数字1-1000。显然,这会令人烦恼,因此我试图创建一个包含范围的列表。在Python 2中,似乎:

some_list = range(1,1000)

本来可以用,但是在Python 3中,范围类似于xrangePython 2?

谁能对此提供一些见识?


1
此外,,some_list[i] == i+1因此您可能根本不需要列表。
njzk2 2014年

1
@RikPoggi。例如,可能需要提供一份绘图功能列表。有时一个范围就足够了,但是一个范围不能被连接(是不可变的),因此,如果您需要为所有要绘制的列表添加一个默认的起始值,则还需要将其转换为一个列表。
SherylHohman '17

Answers:


223

您可以从range对象构造一个列表:

my_list = list(range(1, 1001))

这也是您使用python2.x中的生成器进行操作的方式。通常来说,虽然您可能不需要列表,但因为可以得到my_list[i]更有效(i + 1)的值,如果只需要遍历该列表,则可以依靠range

另请注意,在python2.x上,xrange仍可索引1。这意味着range在python3.x上也具有相同的属性2

1print xrange(30)[12]适用于python2.x

2 python3.x中与1相似的语句是print(range(30)[12])并且也起作用。


4
这绝对是必经之路,但挑剔:这并不是真正的“铸件”
jterrace 2012年

@jterrace将“ cast”更改为“ convert”。你是正确的,因为它不是演员...我真的不知道该怎么称呼它。
mgilson

2
我会说“构造”或“构建”(或可能是“实现”)-因为您没有“将”生成器“转换”为列表,所以您正在从数据源创建新的列表对象成为一名发电机...(但摆姿势只是割开头发,而不是100%肯定我无论如何都喜欢)
乔恩·克莱门茨

2
我的+1代表“构造”,因为它与其他OO语言一致。将list(arg)在其他语言理解为调用的构造函数list的类。实际上,这也是Python的情况。辩论是在构造期间(如在C ++情况下)填充对象,还是仅在第一个自动调用的方法(如Python __init__()方法)期间填充对象,这不能改变基本的抽象概念。我的看法是列表构造函数采用迭代器,并用返回的值填充列表
pepr

2
为什么在jupyter笔记本电脑中出现错误并在shell中可以正常工作?错误:'range' object is not callable
subtleseeker

34

在Pythons <= 3.4中,您可以按照其他建议使用list(range(10)),以使列表超出范围(通常,任何可迭代的列表)。

在Python中3.5以解压缩概括引入的另一种替代方法是*在列表文字中使用[]

>>> r = range(10)
>>> l = [*r]
>>> print(l)
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

尽管这等效于list(r),但是它是字面语法,并且不涉及任何函数调用的事实确实使它执行得更快。如果您需要打高尔夫球,它的字符也更少:-)


4
需要说明的是,您仍然可以将其单行处理:[*range(10)]适用于不需要range初始化任何用途而只需要初始化的情况list。旁注:我最喜欢的(好吧,不是真的)解压缩概括的一部分是,Empty set现在具有文字语法{*()},或者,我称之为单眼猴子运算符。;-)
ShadowRanger

@ShadowRanger就是我最初考虑编写它的方式。我决定更加冗长,以免混淆新的Python用户:-)
Dimitris Fasarakis Hilliard

26

在Python 3.x中,该range()函数具有自己的类型。所以在这种情况下,您必须使用迭代器

list(range(1000))


11
“在这种情况下,您必须使用迭代器”?这到底意味着什么?
user2357112支持Monica's

2
我正在使用python 3.7,并尝试过x = list(range(1000)),但收到错误TypeError:'list'对象不可调用
Earthshaker

@Earthshaker您必须输入错误,例如list(range(1000))()
wjandrea

17

Python3缺少直接获取范围列表的功能的原因是因为最初的Python3设计器在Python2中是新手。他只考虑了range()在for循环中使用函数,因此,该列表永远不需要扩展。实际上,很多时候我们确实需要使用range()函数来生成列表并传递给函数。

因此,在这种情况下,与Python2相比,Python3不那么方便,因为:

  • 在Python2,我们xrange()range() ;
  • 在Python3,我们range()list(range())

尽管如此,您仍然可以通过以下方式使用列表扩展:

[*range(N)]

3
是让不太方便做出list,因为这通常是错误的做法。对于99出的100用例,使实际list是低效和毫无意义的,因为range它本身就像一个不可改变的序列几乎完全不同,有时更有效地引导(如遏制试验ints为O(1),与O(n)listS)。在Python 2中,range即使xrange几乎总是更好的选择,人们还是倾向于默认使用。在Python 3中,您可以显式选择加入list,而不会因使用错误的名称而意外获取。
ShadowRanger

7
关于Python 3设计器及其在Python 2中的专业知识的评论是相当大胆和无礼的。
kazarey,

@kazarey但这是真的吗?python中有很多事情沿这些方面值得怀疑
javadba

1
会投票赞成,尤其是对于拆箱速记来构建列表的投票,但是我同意@kazarey。关于设计师的评论既没有根据(或者至少没有参考文献支持),也没有必要。
Nubarke

12

您实际上不需要在列表中使用数字1-1000。但是,如果由于某些原因您确实需要这些数字,则可以这样做:

[i for i in range(1, 1001)]

清单理解概述:

上面的列表理解转换为:

nums = []
for i in range(1, 1001):
    nums.append(i)

尽管只是2.x版本,但这只是列表理解语法。我知道这可以在python 3中使用,但是不确定是否还有升级的语法

范围开始于第一个参数;但以不包括第二个参数为结束(当提供2个参数时;如果第一个参数保留,则其将从'0'开始)

range(start, end+1)
[start, start+1, .., end]

20
为什么要理解?正义:list(range(1000))
里克·波吉

谢谢!您介意解释为什么我在...中而不是在我中...
船库2012年

我还没有使用python3。因此,我不确定它是如何工作的。我知道理解能力会起作用,但并不是100%都能胜任。但是,如果强制转换有效,那么您是对的,您的方法将更加Python化。
inspectorG4dget

1
@ inspectorG4dget:这不是“广播”,而是list()使用iterable调用构造函数list()给定任何可迭代对象时,构造函数都知道如何创建新列表。
格雷格·休吉尔

4
@ inspectorG4dget:list(range(1000))将在python3中工作,就像list(xrange(1000))在python2中一样
Rik Poggi

4

实际上,如果您想要1-1000(含),请使用range(...)带有参数1和1001:range(1, 1001)range(start, end)函数,因为该函数从开始到(结束-1)(含)。


0

在Python 3中使用范围

这是一个在两个数字之间返回的示例函数

def get_between_numbers(a, b):
    """
    This function will return in between numbers from two numbers.
    :param a:
    :param b:
    :return:
    """
    x = []
    if b < a:
        x.extend(range(b, a))
        x.append(a)
    else:
        x.extend(range(a, b))
        x.append(b)

    return x

结果

print(get_between_numbers(5, 9))
print(get_between_numbers(9, 5))

[5, 6, 7, 8, 9]  
[5, 6, 7, 8, 9]

这似乎在回答一个不同的问题...?
wjandrea

-1

实际上,与Python2相比,这是对Python3的追溯。当然,使用range()和xrange()的Python2比分别使用list(range())和range()的Python3更方便。原因是因为Python3的原始设计人员经验不足,他们只考虑了许多初学者使用范围函数来遍历内存和CPU效率低下的大量元素。但是他们忽略了使用range函数生成数字列表。现在,对他们来说已经变回来为时已晚。

如果要成为Python3的设计师,我将:

  1. 使用irange返回序列迭代器
  2. 使用lrange返回序列表
  3. 使用range返回一个序列迭代器(如果元素数量很大,例如range(9999999))或一个序列列表(如果元素数量很小,例如range(10))

那应该是最佳的。


这如何回答这个问题?
wjandrea

是的,它通过请求Python3开发人员更改和改进Python3来回答这个问题。但是由于它们不那么优雅,它们不太可能会改变。
xuancong84
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.