【问题标题】:python output object not iterablepython输出对象不可迭代
【发布时间】:2020-10-05 17:46:08
【问题描述】:

我在这里看不到我能理解的相关答案。我有一些代码可以输出我认为可以迭代但不能迭代的列表。

代码:

class freqList():
    def __init__(self, startFreq, stopFreq, skip):
        self.startFreq = startFreq
        self.stopFreq = stopFreq
        self.skip = skip

    def __iter__(self):
        pass

    def listFreqs(self):
        return list(range(self.startFreq, self.stopFreq, self.skip))

    def __repr__(self):
        return '{}, {}, {}'.format(
            self.startFreq,
            self.stopFreq,
            self.skip)


    def __str__(self):
        return 'instance object of frequency list, startFreq:{},stopFreq: {},skip: {}'.format(
            self.startFreq,
            self.stopFreq,
            self.skip)


print('\n'*4)
listy = freqList(  1000, 5000, 1000)#range cannot use floats, only ints
print(listy.listFreqs())

print('listy type:', type(listy),'\n')

listy_iter = iter(listy)
print('listy_iter type:', type(listy_iter),'\n')

期望的输出

当我实例化该类时,我希望它返回一个类似列表的可迭代对象。

尝试过

我看到提到 next 需要被覆盖,但我不知道这意味着什么,我是 OOP 的新手,只是刚刚了解了 initstrrepr

【问题讨论】:

  • 那么您的__iter__ 方法只返回无。如果你让它做类似for x in self.listFreqs(): yield x的事情,那么你可以在你的主代码中做for item in listy: ....

标签: python class oop next iterable


【解决方案1】:

我在你的课堂上做了一个小调整

class freqList():
    def __init__(self, startFreq, stopFreq, skip):
        self.startFreq = startFreq
        self.stopFreq = stopFreq
        self.skip = skip
        self._freqs = list(range(self.startFreq, self.stopFreq, self.skip))

    def __iter__(self):
        return iter(self._freqs)

    def listFreqs(self):
        return self._freqs

    def __repr__(self):
        return '{}, {}, {}'.format(
            self.startFreq,
            self.stopFreq,
            self.skip)

    def __str__(self):
        return 'instance object of frequency list, startFreq:{},stopFreq: {},skip: {}'.format(
            self.startFreq,
            self.stopFreq,
            self.skip)

如果您看,我将列表更改为在__init__ 中创建并存储在属性中。然后listFreqs 会调用这个属性来显示整个列表。 迭代器的创建发生在__iter__,其中self._freqs 被iter() 包裹着。

如果您在listFreqs 中定义了您的列表,那么每次调用此方法时它都会重新计算。此外,在调用方法之前,该类不会知道它是什么,因此它无法在其上创建迭代器。

【讨论】:

    【解决方案2】:

    在 python 中,一旦你实例化一个类,你得到的是一个对象。所以不如试试这个

    listy_iter = iter(listy.listFreqs())
    

    这将返回一个列表,它是类freqList()的函数listFreqs的返回类型

    现在listy_iter 会有一个列表

    【讨论】:

      【解决方案3】:

      您的__iter__() 方法实际上必须返回一个迭代器。像这样:

      class freqList():
      def __init__(self, startFreq, stopFreq, skip):
          self.startFreq = startFreq
          self.stopFreq = stopFreq
          self.skip = skip
      
      def __iter__(self):
          return iter(range(self.startFreq, self.stopFreq, self.skip))
      
      def __repr__(self):
          return '{}, {}, {}'.format(
              self.startFreq,
              self.stopFreq,
              self.skip)
      
      
      def __str__(self):
          return 'instance object of frequency list, startFreq:{},stopFreq: {},skip: {}'.format(
              self.startFreq,
              self.stopFreq,
              self.skip)
      
      
      listy = freqList(  1000, 5000, 1000)
      
      for l in listy:
          print(l)
      

      【讨论】:

        【解决方案4】:

        尝试详细说明您的问题。 根据我的理解,以下是您正在寻找的内容

          def __iter__(self):
              iter_list = list(range(self.startFreq, self.stopFreq, self.skip))
              for i in iter_list:
                   yield i
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2021-12-13
          • 2013-12-01
          • 2015-04-14
          • 2022-07-01
          • 2022-09-30
          • 2014-04-26
          • 2019-02-10
          • 2015-04-06
          相关资源
          最近更新 更多