1. ホーム
  2. python

[解決済み】TypeError:'type'オブジェクトはiterableではありません - オブジェクトインスタンスを繰り返し処理する。

2022-01-21 06:27:21

質問

あるプロジェクトで、クラスの1つを反復可能にしたいと思います。私の知る限りでは、メタクラスを使用することでそれが可能です。

まず、メタクラスがどのように機能するかを理解したいと思います。そこで、私自身の実践例として、Carクラスを作成した例を紹介したいと思います。ここでは、Carクラスのオブジェクトを反復可能にして、その名前をmain関数で表示するようにしたいと思います。

コード例は以下の通りです。

__author__ = 'mirind4'

class IterableCar(type):
    def __iter__(self):
        return iter(self.__name__)

class Car(object):
    __metaclass__ = IterableCar

    def __init__(self, name):
        self.name = name


if __name__=='__main__':

    car1 = Car('Mercedes')
    car2 = Car('Toyota')
    for cars in Car:
        print (cars.name)

しかし、残念ながらTypeErrorが発生しました。

TypeError: 'type' object is not iterable

私のコードのどこに間違いがあるのか、親切に教えていただけませんか?今まで、このサイトやインターネット上で同じような問題質問をチェックしましたが、何が問題なのかわかりません。私はpython 3.4を使っています。 ありがとうございました。

どのように解決するのですか?

私の知る限り、メタクラスを使用してクラスオブジェクトを反復可能にすることはうまくいきます。

from __future__ import print_function

class IterableCar(type):
    def __iter__(cls):
        return iter(cls.__name__)

class Car(object):
    __metaclass__ = IterableCar

    def __init__(self, name):
        self.name = name


if __name__=='__main__':

    car1 = Car('Mercedes')
    car2 = Car('Toyota')
    for cars in Car:
        print (cars)

結果が出る。

mgilson$ python ~/sandbox/test.py 
C
a
r


実際に生成された車を追跡している例です。

from __future__ import print_function
import weakref

class IterableCar(type):

    _cars = weakref.WeakSet()

    def __iter__(cls):
        return iter(cls._cars)

    def add_car(cls, car):
        cls._cars.add(car)


class Car(object):
    __metaclass__ = IterableCar

    def __init__(self, name):
        self.__class__.add_car(self)
        self.name = name


if __name__=='__main__':

    car1 = Car('Mercedes')
    car2 = Car('Toyota')
    for cars in Car:
        print (cars.name)

Python3.xを使用している場合、メタクラスを使用するために、あなたはそうすることに注意してください。

class Car(metaclass=IterableCar):
    ...

よりも、むしろ

class Car(object):
    __metaclass__ = IterableCar

というメッセージが表示され、あなたが経験している問題を説明する可能性があります。