Уведомления

Группа в Telegram: @pythonsu

#1 Ноя. 25, 2011 14:30:55

dissdoc
От:
Зарегистрирован: 2009-12-12
Сообщения: 273
Репутация: +  0  -
Профиль   Отправить e-mail  

Создать новый класс по подобию старого

Всем привет. Вопрос такой. Как мне создать новый класс по образу и подобию исходного. Есть исходных класс SourceClass. Как только не пытался. Что делаю
Хочу вот что-то вроде этого

# Source Class
cls = SourceClass()
# Есть у него значения переменных
cls.name = 'MyName'

# Теперь создаю новый класс
# так
new_class = super(object, cls).__new__
# так
new_class = cls.__new__(cls.__name__, cls.__bases__, cls.__dict__)
# и еще миллион способов :( Ничего не получается
Идея, чтобы new_class был того же типа и с теми же параметрами, что и SourceClass



Отредактировано (Ноя. 25, 2011 14:31:39)

Офлайн

#2 Ноя. 25, 2011 15:34:34

o7412369815963
От:
Зарегистрирован: 2009-06-17
Сообщения: 1986
Репутация: +  32  -
Профиль   Отправить e-mail  

Создать новый класс по подобию старого

import copy

class SourceClass(object):
def foo(self):
return 'foo'

cls = SourceClass()
cls.name = 'MyName'

B = type('B',(cls.__class__,),copy.deepcopy(cls.__dict__))
b = B()

print b.foo(), b.name
это нужно?

> Идея, чтобы new_class был того же типа и с теми же параметрами, что и SourceClass
с теми же или с такими же?

если нужно скопировать экземпляр, то можно выполнить copy.deepcopy

Зачем это все?

Офлайн

#3 Ноя. 25, 2011 21:28:36

dissdoc
От:
Зарегистрирован: 2009-12-12
Сообщения: 273
Репутация: +  0  -
Профиль   Отправить e-mail  

Создать новый класс по подобию старого

Это все нужно для создания динамических классов, когда заранее не известно какой из классов SourceClass или TestClass будет являться шаблоном)
То или не то, сейчас проверить не могу. Но глубокое копирование очень и очень подкупает. Нужно проверить..



Офлайн

#4 Ноя. 26, 2011 18:16:08

dissdoc
От:
Зарегистрирован: 2009-12-12
Сообщения: 273
Репутация: +  0  -
Профиль   Отправить e-mail  

Создать новый класс по подобию старого

Это все же не то что нужно. Необходимо при создании класса, как бы вызвать метод __new__
Точнее. Попробую более подробно описать проблему.

Фактически она должна вовзращать что-то вроде cls() (или __new__)
что-то вроде

return super(MyClass, cls).__new__
Но я не пойму, что я делаю не так, какой первый параметр вставлять, если нам известен cls (<class ‘__main__.MyClass’>) со всеми методами и параметрами



Офлайн

#5 Ноя. 26, 2011 19:03:15

dissdoc
От:
Зарегистрирован: 2009-12-12
Сообщения: 273
Репутация: +  0  -
Профиль   Отправить e-mail  

Создать новый класс по подобию старого

Сам разобрался. Нашел в книге Бизли

new_cls = cls.__new__(cls, cls.__bases__, cls.__dict__)
if isinstance(new_cls, cls):
cls.__init__(new_cls)



Офлайн

#6 Ноя. 26, 2011 21:32:30

Fibio
От:
Зарегистрирован: 2010-09-14
Сообщения: 74
Репутация: +  2  -
Профиль   Отправить e-mail  

Создать новый класс по подобию старого

class NewClass(SourceClass): pass - а так нельзя?



Офлайн

#7 Ноя. 26, 2011 22:28:49

bw
От:
Зарегистрирован: 2007-09-26
Сообщения: 938
Репутация: +  20  -
Профиль   Адрес электронной почты  

Создать новый класс по подобию старого

>>> new_cls = cls.__new__(cls, cls.__bases__, cls.__dict__)
>>> cls.__init__(new_cls)

Эквивалентно:
>>> new_cls = cls()

Ну и понятно, что new_cls, это никакой не класс, а экземпляр класса cls.
Я никак не могу понять что требуется.

> Это все нужно для создания динамических классов…
>>> new_cls = new.classobj('new_cls', (base_cls1,), {})

Что значит “динамических классов”? В Python всё динамическое. Предыдущая запись эквивалентна:
>>> class new_cls(base_cls1): pass

..bw



Офлайн

#8 Ноя. 27, 2011 08:45:53

o7412369815963
От:
Зарегистрирован: 2009-06-17
Сообщения: 1986
Репутация: +  32  -
Профиль   Отправить e-mail  

Создать новый класс по подобию старого

bw
Я никак не могу понять что требуется.
и я.

Попробовал запустить на ру2.7 и 3.2, код не работает - cls.__new__ принимает только 1 параметр
dissdoc
Сам разобрался. Нашел в книге Бизли
new_cls = cls.__new__(cls, cls.__bases__, cls.__dict__)
if isinstance(new_cls, cls):
cls.__init__(new_cls)
Может автор хочет метаклассы?
см http://www.py-my.ru/post/4e04bc2c1d41c86c33000000

Офлайн

#9 Ноя. 27, 2011 10:23:40

bw
От:
Зарегистрирован: 2007-09-26
Сообщения: 938
Репутация: +  20  -
Профиль   Адрес электронной почты  

Создать новый класс по подобию старого

> cls.__new__ принимает только 1 параметр
Вообще-то да, не обратил внимания на этот говнокод. Он же принимает класс и аргументы для инициализации экземпляра.

..bw



Офлайн

#10 Ноя. 27, 2011 13:47:32

dissdoc
От:
Зарегистрирован: 2009-12-12
Сообщения: 273
Репутация: +  0  -
Профиль   Отправить e-mail  

Создать новый класс по подобию старого

Да, у меня есть в коде метаклассы. Я не мог доходчиво объяснить это. Именно, создавал экземпляр класса, так, чтобы он принимал методы и метакласса и класса родителя.
И отработал мой “говнокод” так, как мне этого требовалось

По поводу кода new_cls = cls() - улыбнуло, потому что я не догадался сделать это так просто) спасибо!



Офлайн

Board footer

Модераторировать

Powered by DjangoBB

Lo-Fi Version