Как создавать объекты на лету в питоне? - PullRequest
14 голосов
/ 20 декабря 2011

Как мне создавать объекты на лету в Python?Я часто хочу передать информацию моим шаблонам Django в следующем формате:

{'test': [a1, a2, b2], 'test2': 'something else', 'test3': 1}

, что делает шаблон неопрятным.поэтому я думаю, что лучше просто создать объект, который выглядит как:

class testclass():
    self.test = [a1,a2,b2]
    self.test2 = 'someting else'
    self.test3 = 1
testobj = testclass()

, поэтому я могу сделать:

{{ testobj.test }}
{{ testobj.test2 }}
{{ testobj.test3 }}

вместо вызова словаря.

Так какМне просто нужен этот объект один раз, возможно ли его создать без предварительного написания класса?Есть ли сокращенный код?Можно ли так делать или это плохой Python?

Ответы [ 6 ]

25 голосов
/ 20 декабря 2011

Вы можете использовать встроенную функцию type :

testobj = type('testclass', (object,), 
                 {'test':[a1,a2,b2], 'test2':'something else', 'test3':1})()

Но в этом конкретном случае (объект данных для шаблонов Django) вам следует использовать решение @ Xion.

23 голосов
/ 20 декабря 2011

В шаблонах Django точечная нотация (testobj.test) может преобразовываться в оператор Python []. Это означает, что все, что вам нужно, это обычный дикт:

testobj = {'test':[a1,a2,b2], 'test2':'something else', 'test3':1}

Передайте его как переменную testobj в свой шаблон, и вы можете свободно использовать {{ testobj.test }} и подобные выражения внутри вашего шаблона. Они будут переведены на testobj['test']. Здесь не нужно выделенного класса.

10 голосов
/ 26 октября 2016

Есть еще одно решение в Python 3.3 + types.SimpleNamespace

from types import SimpleNamespace
test_obj = SimpleNamespace(a=1, b=lambda: {'hello': 42})

test_obj.a
test_obj.b()
9 голосов
/ 20 декабря 2011

Использование collections.namedtuple.

1 голос
/ 17 декабря 2017

использовать тип функции здания: документ

>>> class X:
...     a = 1
...
>>> X = type('X', (object,), dict(a=1))

первый и второй X идентичны

0 голосов
/ 20 декабря 2011

Код ниже также требует создания класса, однако он короче:

 >>>d = {'test':['a1','a2','b2'], 'test2':'something else', 'test3':1}
 >>> class Test(object):
 ...  def __init__(self):
 ...   self.__dict__.update(d)
 >>> a = Test()
 >>> a.test
 ['a1', 'a2', 'b2']
 >>> a.test2
 'something else'
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...