Создание экземпляра класса в цикле и его обновление

1

Скажем, у меня есть набор данных ("test.csv"):

Name,Fruit,Price
John,Apple,1.00
Steve,Apple,1.00
John,Mango,2.00
Adam,Apple,1.00
Steve,Banana,1.00

Хотя есть несколько простых способов сделать это, я хотел бы организовать эту информацию как класс в python. Итак, в идеале, экземпляр класса будет выглядеть так:

{'name': 'John', 'Fruits': ['Apple','Mango'], 'Price':[1.00, 2.00]}

Мой подход к загрузке набора данных в класс - хранить каждый экземпляр в списке.

class org(object):
    def __init__(self,name,fruit,price):
        self.name = name
        self.fruit = [fruit]
        self.price = [price]

    classes = []
    with open('test.csv') as f:
        for line in f:
            if not 'Name' in line:
                linesp=line.rstrip().split(',')
                name = linesp[0]
                fruit = linesp[1]
                price = linesp[2]
                inst = org(name,fruit,price)
                classes.append(inst)
    for c in classes:
        print (c.__dict__)
  1. В этом случае, как я узнаю, что "Джон" уже существует как экземпляр?

  2. Если да, то как мне обновить "Джон"? С классом?

@classmethod
    def update(cls, value):
        cls.fruit.append(fruit)
Теги:
class
loops
oop

1 ответ

2
Лучший ответ

Нет необходимости в каких-либо специальных обновлениях для ваших экземпляров. Атрибуты вашего класса являются общедоступными, поэтому просто обращайтесь к ним для обновления.

Если вы настаиваете на использовании списка в качестве контейнера экземпляра, вы можете сделать sth. как это:

classes = []
with open('test.csv') as f:
    for line in f:
        if not 'Name' in line:
            name,fruit,price=line.rstrip().split(',')
            exists = [inst for inst in classes if inst.name == name]
            if exists:
                exists[0].fruit.append(fruit)
                exists[0].price.append(price)
            else:
                classes.append(org(name,fruit,price))
for c in classes:
    print (c.__dict__)

Однако я рекомендую использовать вместо этого dict, потому что он упрощает поиск и доступ к экземплярам

classes = {}
with open('test.csv') as f:
    for line in f:
        if not 'Name' in line:
            name,fruit,price=line.rstrip().split(',')
            if name in classes:
                classes.get(name).fruit.append(fruit)
                classes.get(name).price.append(price)
            else:
                classes.update({name: org(name,fruit,price)})

for c in classes.values():
    print (c.__dict__)

Оба решения дадут вам то же самое:

{'name': 'John', 'fruit': ['Apple', 'Mango'], 'price': ['1.00', '2.00']}
{'name': 'Steve', 'fruit': ['Apple', 'Banana'], 'price': ['1.00', '1.00']}
{'name': 'Adam', 'fruit': ['Apple'], 'price': ['1.00']}

Ради полноты, то, что @MadPhysicist ниже в комментариях, вероятно, означает неуклюжим способом обновления dict, заключается в том, что я использую методы dict вместо доступа к элементам по подписке.

# update existing instance in the dict
classes[name].fruit.append(fruit)

# add new instance to the dict
classes[name] = org(name, fruit, price)

Я лично считаю, что это несколько уродливо, поэтому я стараюсь использовать методы :)

  • 0
    Идея использовать диктовку верна. +1 за это. То, как вы обновляете диктовку, очень неуклюже.
  • 0
    @MadPhysicist Хотите уточнить, почему вы считаете это неуклюжим? :)
Показать ещё 3 комментария

Ещё вопросы

Сообщество Overcoder
Наверх
Меню