Python Range类如何自动执行?

Python Range类如何自动执行?,python,Python,我正在用Python学习数据结构和算法。对于我正在使用的教科书,我重新审视了一个我从未理解的问题。对于下面的用户构建的范围类,为什么像[x代表范围(0,5)]中的x这样的东西会起作用?本质上,为什么索引会自动移动?没有对getitem或len的调用 我已经阅读了Python教程和类部分,但还没有弄明白这一点 class Range: """A class that mimic's the built-in range class.""" def __init__(self, start

我正在用Python学习数据结构和算法。对于我正在使用的教科书,我重新审视了一个我从未理解的问题。对于下面的用户构建的范围类,为什么像[x代表范围(0,5)]中的x这样的东西会起作用?本质上,为什么索引会自动移动?没有对getitem或len的调用

我已经阅读了Python教程和类部分,但还没有弄明白这一点

class Range:
  """A class that mimic's the built-in range class."""

  def __init__(self, start, stop=None, step=1):
    """Initialize a Range instance.

    Semantics is similar to built-in range class.
    """
    if step == 0:
      raise ValueError('step cannot be 0')

    if stop is None:                  # special case of range(n)
      start, stop = 0, start          # should be treated as if range(0,n)

    # calculate the effective length once
    self._length = max(0, (stop - start + step - 1) // step)

    # need knowledge of start and step (but not stop) to support __getitem__
    self._start = start
    self._step = step

  def __len__(self):
    """Return number of entries in the range."""
    return self._length

  def __getitem__(self, k):
    """Return entry at index k (using standard interpretation if negative)."""
    if k < 0:
      k += len(self)                  # attempt to convert negative index

    if not 0 <= k < self._length:
      raise IndexError('index out of range')

    return self._start + k * self._step
类别范围:
“”“模拟内置范围类的类。”“”
定义初始化(自、启动、停止=无,步骤=1):
“”“初始化范围实例。
语义类似于内置的range类。
"""
如果步骤==0:
raise VALUERROR('步骤不能为0')
如果停止为无:#范围的特殊情况(n)
start,stop=0,start#应视为范围(0,n)
#计算一次有效长度
self._length=max(0,(停止-启动+步骤-1)//步骤)
#需要了解开始和步骤(但不是停止)以支持__
self.\u start=start
自我。_步骤=步骤
定义(自我):
“”“返回范围内的项目数。”“”
返回自我长度
定义获取项目(self,k):
“”“返回索引k处的条目(如果为负数,则使用标准解释)。”
如果k<0:
k+=len(self)#尝试转换负指数

如果不是0,这是因为Range类实现了有效的所有必要的方法,即
\uuu len\uuu
\uu getitem\uuu
方法。这允许它自动用作iterable,如中所述:

Iterables可用于for循环和许多其他需要 需要序列(zip(),map(),…)。当一个iterable对象 作为参数传递给内置函数iter(),它返回 对象的迭代器。此迭代器适用于在 一组值。使用iterables时,通常不需要 调用iter()或自己处理迭代器对象。for声明 这样做会自动为您创建一个临时的未命名变量 在循环期间保持迭代器。另见迭代器, 序列和生成器


这是因为Range类实现了成为一个有效类所必需的所有功能,即
\uuuuu len\uuuu
\uuu getitem\uuuu
方法。这允许它自动用作iterable,如中所述:

Iterables可用于for循环和许多其他需要 需要序列(zip(),map(),…)。当一个iterable对象 作为参数传递给内置函数iter(),它返回 对象的迭代器。此迭代器适用于在 一组值。使用iterables时,通常不需要 调用iter()或自己处理迭代器对象。for声明 这样做会自动为您创建一个临时的未命名变量 在循环期间保持迭代器。另见迭代器, 序列和生成器


实际上,
\uuuu getitem\uuuuu
本身就足够了;它将使用
0
调用
\uuuuuu getitem\uuuuuuuuuuuuuuuuuuuuuuuuuuu
,然后调用
1
,然后调用
2
,等等,直到
\uuuuuu getitem\uuuuuuuuuuuuuuuuuuuu
引发
索引器(它会抑制该索引器,悄悄结束迭代;任何其他异常都会正常冒泡)<代码>\uuuu len\uuuu
不是必需的,即使存在也不会使用。正如您自己的链接所指出的,iterables是“使用
\uuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuo()方法或使用
\uuuuuuuuuuuuuuuuuuuuuuuuuuu.@shadowranger你在哪个时区?@roganjosh:UTC-5。但是,当我无法专注于真正的工作时,我会在随机的时间发表文章,作为一种净化心灵的方法。:-)实际上,
\uuuu getitem\uuuuu
本身就足够了;它将使用
0
调用
\uuuuuu getitem\uuuuuuuuuuuuuuuuuuuuuuuuuuu
,然后调用
1
,然后调用
2
,等等,直到
\uuuuuu getitem\uuuuuuuuuuuuuuuuuuuu
引发
索引器(它会抑制该索引器,悄悄结束迭代;任何其他异常都会正常冒泡)<代码>\uuuu len\uuuu
不是必需的,即使存在也不会使用。正如您自己的链接所指出的,iterables是“使用
\uuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuo()方法或使用
\uuuuuuuuuuuuuuuuuuuuuuuuuuu.@shadowranger你在哪个时区?@roganjosh:UTC-5。但是,当我无法专注于真正的工作时,我会在随机的时间发表文章,作为一种净化心灵的方法。:-)注意:虽然
\uuuuu getitem\uuuuuuuuu
已经足够了,但为了效率起见,实现
\uuuuuuuuu iter\uuuuuuuuuu
作为生成器函数通常是个好主意;
\uu getitem\uuuuuu
中涉及的所有边界检查和重复重新计算使得它比任何合理实现的
\uuuu iter\uuuu
慢得多。在本地测试中,基于
while
循环的生成器
\uuuu iter\uuuu
在较大范围内将运行时间缩短约三分之二,即使在较小范围内也将运行时间缩短一半。请注意,实际的
范围
所需时间甚至是基于
的重新实施所需时间的十分之一,因此,如果不是课堂练习,请使用附带的电池。:-)注意:虽然
\uuuuu getitem\uuuuuuuuu
已经足够了,但为了效率起见,实现
\uuuuuuuuu iter\uuuuuuuuuu
作为生成器函数通常是个好主意;
\uu getitem\uuuuuu
中涉及的所有边界检查和重复重新计算使得它比任何合理实现的
\uuuu iter\uuuu
慢得多。在本地测试中,基于
while
循环的生成器
\uuuu iter\uuuu
在较大范围内将运行时间缩短约三分之二,即使在较小范围内也将运行时间缩短一半