Уведомления

Группа в Telegram: @pythonsu

#1 Май 15, 2017 11:06:44

4kpt_V
От: Харьков
Зарегистрирован: 2017-02-19
Сообщения: 299
Репутация: +  12  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

 #
if __name__ == '__main__':
    a = SomeClass()
    b = SomeClass()
    print(id(a.myName))
    print(id(b.myName))
    print(a.myName)
    print(b.myName)
    a.myName = 'my name is A'
    print(a.myName)
    print(b.myName)
    b.myName = 'my name is B'
    print(a.myName)
    print(b.myName)
    del a.myName

Это раз…

И как Вы думаете? В какой момент выполняется эта строка?
 #
class SomeClass:
    myName = Name()  # вот эта вот...

Офлайн

#2 Май 15, 2017 11:39:42

alexgreg
Зарегистрирован: 2017-05-15
Сообщения: 26
Репутация: +  0  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

PEHDOM
вопрос, вам это надо для чего?
для понимания тонкостей работы протокола дескриптора в рамках изучения расширенных методов управления атрибутов класса/экземпляра класса

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

Офлайн

#3 Май 15, 2017 11:51:35

alexgreg
Зарегистрирован: 2017-05-15
Сообщения: 26
Репутация: +  0  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

4kpt_V
И как Вы думаете? В какой момент выполняется эта строка?

Я согласен, если бы класс Name был обычным классом без протокола дескриптора. Дело в том, что аналогичное объявление свойств класса, но с наличием атрибутов в этом же классе (в примере - класс D), отрабатывает:

  
class Nn: # дескриптор свойств nn
    """ счётчик обращений к name """
    def __get__(self, instance, owner):
        return owner._nn
    
    def __set__(self, instance, value):
        raise AttributeError('Нельзя изменить счётчик')
    
    def __delete__(self, instance):
        raise AttributeError('Нельзя удалить счётчик')
class Name: # дескриптор свойств name
    """ имя экземпляра """
    def __get__(self, instance, owner):
        owner._nn += 1
        return '[%d] %s' % (owner._nn, instance._name)
    
    def __set__(self, instance, value):
        instance._name = value
    def __delete__(self, instance):
        raise AttributeError('Нельзя удалить имя экземпляра')
class D: # класс-клиент
    def __init__(self):
        D._nn = 0
        self._name = 'по-умолчанию'
    nn = Nn()
    name = Name()
#---------------------------------------------------------------------------------
if __name__ == '__main__':
    a, b, c = D(), D(), D()
    a.name = 'my name is A'
    b.name = 'my name is B'
    c.name = 'my name is C'
    print(a.name)
    print(b.name)
    print(c.name)
    print(a.nn)
    print(b.nn)
    print(c.nn)

Результаты:

 ================= RESTART: D:\web.py\attrs\mydescriptors.py =================
[1] my name is A
[2] my name is B
[3] my name is C
3
3
3
>>>


В этом примере свойство nn - общий для всех экземпляров счётчик обращений к свойству name, а name - имя экземпляра (для каждого своё)

Отредактировано alexgreg (Май 15, 2017 12:12:05)

Офлайн

#4 Май 15, 2017 12:12:12

4kpt_V
От: Харьков
Зарегистрирован: 2017-02-19
Сообщения: 299
Репутация: +  12  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

Я задал простой вопрос. Жду на него ответа.

P.S. Хватит выделять черным. У форумчан со зрением пока все ОК

Отредактировано 4kpt_V (Май 15, 2017 12:12:39)

Офлайн

#5 Май 15, 2017 12:30:47

alexgreg
Зарегистрирован: 2017-05-15
Сообщения: 26
Репутация: +  0  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

4kpt_V
Я задал простой вопрос. Жду на него ответа.
Думаю, что при импорте/запуске модуля


Аналогичная строка из второго примера:
 class D: # класс-клиент
    def __init__(self):
        D._nn = 0
        self._name = 'по-умолчанию'
    nn = Nn()
    name = Name()  #  вот эта ... 


В чём принципиальное отличие?

Отредактировано alexgreg (Май 15, 2017 12:42:28)

Офлайн

#6 Май 15, 2017 12:42:33

4kpt_V
От: Харьков
Зарегистрирован: 2017-02-19
Сообщения: 299
Репутация: +  12  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

Верно. Т.е. при импорте или запуске модуля создается класс и с атрибутом класса (внимание! класса), связывается объект (внимание! объект) дескриптора. Потом вы на основе этого класса наделали объектов, но при этом атрибут остался атрибутом класса. Не объекта! Изменяя этот атрибут через объект (который Вы наштамповали с использованием класса как формы) Вы все равно меняете атрибут класса, который наследуют через него все объекты. Соответственно в них он тоже меняется.

P.S. Не знаю как еще проще объяснить Надеюсь понятно.

Офлайн

#7 Май 15, 2017 12:46:04

alexgreg
Зарегистрирован: 2017-05-15
Сообщения: 26
Репутация: +  0  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

4kpt_V
P.S. Не знаю как еще проще объяснить Надеюсь понятно.
к предыдущему моему посту: объявление аналогичное, но работает как надо

Офлайн

#8 Май 15, 2017 12:47:04

4kpt_V
От: Харьков
Зарегистрирован: 2017-02-19
Сообщения: 299
Репутация: +  12  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

alexgreg
Вы читаете вообще что я пишу?

Офлайн

#9 Май 15, 2017 12:50:47

alexgreg
Зарегистрирован: 2017-05-15
Сообщения: 26
Репутация: +  0  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

4kpt_V
Вы читаете вообще что я пишу?
Онлайн
конечно

Офлайн

#10 Май 15, 2017 12:51:22

4kpt_V
От: Харьков
Зарегистрирован: 2017-02-19
Сообщения: 299
Репутация: +  12  -
Профиль   Отправить e-mail  

Дескриптор с self.value (Descriptor with self.value)

Что из того, что я написал Вам не понятно?

Офлайн

Board footer

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

Powered by DjangoBB

Lo-Fi Version