Функция по атрибуту init - PullRequest
0 голосов
/ 21 января 2019

Мне нужно вызвать функцию перед инициализацией атрибута, желательно с использованием класса данных python3.7, также можно назвать namedtuple.

Этот код делает что-то похожее, и имя атрибута просто набирается один раз, но это очень запутаннои я не знаю, как поддерживать значения по умолчанию.Я уверен, что есть лучший и более питонский способ сделать это.

from collections import namedtuple

person = {
    'name': (lambda value: value.upper()),
    'age': (lambda value: value*2),
}



class Person(namedtuple("Person", person.keys())):
    def __new__(cls, **kwargs):
        return super().__new__(cls, **{k:person[k](v) for k, v in kwargs.items() if v is not None and k in person})


l = Person(**{'name': 'gesiel', 'age': 34})
print(l)

1 Ответ

0 голосов
/ 22 января 2019

Самый простой способ сделать это - просто иметь обычный класс данных с вспомогательной функцией, которая выполняет преобразования перед построением объекта Person.

@dataclass
class Person:
    age: int
    name: str

def make_person(age, name):
    return Person(age*2, name.upper())

person = make_person(100, 'patrick')
print(person.age, person.name)
# 200 PATRICK

Другой вариант - использовать Обработка после инициализации для изменения значений.

@dataclass
class Person:
    age: int
    name: str
    def __post_init__(self):
        self.age  = self.age * 2
        self.name = self.name.upper()

person = Person(100, 'patrick')
print(person.age, person.name)
# 200 PATRICK
...