Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/363.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 for循环如何计算其参数_Python_Python 2.7_Python 3.x_For Loop - Fatal编程技术网

Python for循环如何计算其参数

Python for循环如何计算其参数,python,python-2.7,python-3.x,for-loop,Python,Python 2.7,Python 3.x,For Loop,我的问题很简单 for循环是否每次都计算它使用的参数 例如: for i in range(300): python是否为该循环的每个迭代创建了一个包含300项的列表 如果是,这是一种避免方法吗 lst = range(300) for i in lst: #loop body 类似这样的代码示例也是如此 for i in reversed(lst): for k in range(len(lst)): 是每次应用反向过程,还是每次迭代计算长度?(我对蟒蛇2和蟒蛇3都这样要求)

我的问题很简单

for
循环是否每次都计算它使用的参数

例如:

for i in range(300):
python是否为该循环的每个迭代创建了一个包含300项的列表

如果是,这是一种避免方法吗

lst = range(300)
for i in lst:
    #loop body
类似这样的代码示例也是如此

for i in reversed(lst):

for k in range(len(lst)):
是每次应用反向过程,还是每次迭代计算长度?(我对蟒蛇2和蟒蛇3都这样要求)


如果不是,Python在迭代iterable时如何计算iterable上的更改?

不用担心,迭代器将只计算一次。它最终大致相当于这样的代码:

it = iter(range(300))
while True:
    try:
        i = next(it)
    except StopIteration:
        break
    ... body of loop ...

请注意,它不是完全等效的,因为
break
的工作方式不同。请记住,您可以将
else
添加到
for
循环中,但这在上述代码中不起作用。

在这种情况下,Range会创建一个300整数的数组。它不会创建300整数的数组300次。它不是很有效率。如果您使用xrange,它将创建一个不会占用太多内存的iterable对象

示例.py
创建什么对象取决于在返回上循环的Iterable的
\uuuuu iter\uuuu
方法

通常,Python在迭代本身不是迭代器的Iterable时会创建一个迭代器。在Python2中,
range
返回一个列表,该列表是一个Iterable,具有一个返回迭代器的
\uuuuuuuuuuu
方法

>>> from collections import Iterable, Iterator
>>> isinstance(range(300), Iterable)
True
>>> isinstance(range(300), Iterator)
False
>>> isinstance(iter(range(300)), Iterator)
True
in-sequence:do something的
语法基本上是这样做的简写:

it = iter(some_iterable) # get Iterator from Iterable, if some_iterable is already an Iterator, __iter__ returns self by convention
while True:
    try:
        next_item = next(it)
        # do something with the item
    except StopIteration:
        break
下面是一个演示,其中包含一些打印语句,以澄清使用for循环时发生的情况:

class CapitalIterable(object):
    'when iterated over, yields capitalized words of string initialized with'
    def __init__(self, stri):
        self.stri = stri

    def __iter__(self):
        print('__iter__ has been called')
        return CapitalIterator(self.stri)

        # instead of returning a custom CapitalIterator, we could also
        # return iter(self.stri.title().split())
        # because the built in list has an __iter__ method

class CapitalIterator(object):
    def __init__(self, stri):
        self.items = stri.title().split()
        self.index = 0

    def next(self): # python3: __next__
        print('__next__ has been called')
        try:
            item = self.items[self.index]
            self.index += 1
            return item
        except IndexError:
            raise StopIteration

    def __iter__(self):
        return self

c = CapitalIterable('The quick brown fox jumps over the lazy dog.')
for x in c:
    print(x)
输出:

__iter__ has been called
__next__ has been called
The
__next__ has been called
Quick
__next__ has been called
Brown
__next__ has been called
Fox
__next__ has been called
Jumps
__next__ has been called
Over
__next__ has been called
The
__next__ has been called
Lazy
__next__ has been called
Dog.
__next__ has been called

如您所见,
\uu iter\uu
只被调用一次,因此只创建了一个迭代器对象。

或者在Python2或Python3中,
i=next(it)
。此外,尽管在整个循环中使用的是同一个迭代器,但它所迭代的对象可能会发生变化,这就是为什么不建议这样做的原因,例如,在迭代列表元素时修改列表。谢谢,我刚刚找到了一种方法来检查我所问的问题。我可以定义一个返回iterable(不是生成器)的函数,在其中添加一个print语句,然后检查它将打印多少次。如果您对优化感兴趣,我会看看“将代码转换为漂亮的、惯用的Python”-很多很棒的Python代码。您已经得到了答案,但值得一提的是这个范围()仅返回Python 2中的列表。在Python3中,
range(300)
创建一个range对象,它是一个具有内部状态的生成器。这意味着您可以在不耗尽内存的情况下执行诸如
range(10000000000000000)
之类的操作。在Python2中,可以使用
xrange
获得相同的效果。
__iter__ has been called
__next__ has been called
The
__next__ has been called
Quick
__next__ has been called
Brown
__next__ has been called
Fox
__next__ has been called
Jumps
__next__ has been called
Over
__next__ has been called
The
__next__ has been called
Lazy
__next__ has been called
Dog.
__next__ has been called