0

次のような辞書のリストがあるとします。

list_of_dicts = [
    {'id': 'something', type: 'type_a', blah...},
    {'id': 'anotherthing', type: 'type_b', blah...},
    {'id': 'yetanotherthing', type: 'type_c', blah...},
    etc.
]

そして、私は次のようないくつかのオブジェクトを持っています:

class Base(object):
    def __init__(self, blah):
        self.blah = blah

class TypeA(Base):

class TypeB(Base):

class TypeC(Base):

etc.

リストを繰り返し処理し、条件に応じて、次のように言いましょう。

for elem in list_of_dicts:
    if elem['type'] == 'type_a':
        my_obj = TypeA(blah)
    elif elem['type'] == 'type_b':
        my_obj = TypeB(blah)

    etc.

私は多くのクラスを持っているかもしれません。適切なオブジェクトを選択するための非常に長い if/elif を回避するにはどうすればよいですか? これを達成する動的な方法はありますか?さらに良いことに、すべてのタイプのオブジェクトを明示的に選択して設定しないことで、賢くなりすぎているのでしょうか?

各オブジェクトには設定する属性が 10 個以上ある場合があり、この if/elif ブロックは非常に長く、読み取り/保守が難しくなっています。

アップデート:

おそらく答えは、私がこれについて完全に間違っているということです。私の当初の目標は、このネストされた辞書があり、各辞書要素を特定の方法で「クリーンアップ」/強化したいということです。'type'=='type_a' の要素の場合、いくつかの新しいキーを追加したいと考えています。'type'=='type_b' の場合、1 つまたは 2 つのキーの名前を編集したいかもしれません。'type'=='type_c' の場合、特定のキーの値を編集したいなどです。30、40、おそらく 50 の異なるタイプが存在する可能性があります。したがって、「乱雑な」ネストされた dict から始めて、「きれいな」ものを取り戻し、自分のやり方を変更しました。

私の最初のアプローチは、タイプごとにクラスを用意することでした。@propertyそして、各クラスは、特定の属性を特定の方法で設定する独自の装飾されたメソッドを持つことができます。そして、それらはすべて、すべての属性をキーとして持つ辞書を返すメソッドを持つ同じ基本クラスから継承します。

4

2 に答える 2

0

次のような小さな class_factory 関数を使用できます: (基本クラスのロジックも少し改善しました)

list_of_dicts = [
    {'id': 'something', 'type': 'type_a', 'name': 'batman'},
    {'id': 'anotherthing', 'type': 'type_b', 'city': 'NYC', 'country': 'USA'},
    {'id': 'yetanotherthing', 'type': 'type_c', 'foo': 'bar'},
    {'id': 'one with no type', 'best_city': 'Paris'},
    {'id': 'one with an unknown type', 'type': 'type_z', 'result': 'it still works'},

]

class Base(object):
    def __init__(self, **kwargs):
        kwargs.pop('type', None)
        for attr_name, attr_value in kwargs.items():
            setattr(self, attr_name, attr_value)

class TypeA(Base):
    pass

class TypeB(Base):
    pass

class TypeC(Base):
    pass


def class_factory(a_dict):

    mapping = {
        'type_a': TypeA,
        'type_b': TypeB,
        'type_c': TypeC,
    }

    return mapping.get(a_dict.get('type'), Base)


my_dynamic_objects = []
for elem in list_of_dicts:
    my_dynamic_objects.append(class_factory(elem)(**elem))
于 2015-11-12T21:43:01.713 に答える