Строки документации для дескрипторов PythonPython

Программы на Python
Ответить
Anonymous
 Строки документации для дескрипторов Python

Сообщение Anonymous »

Я столкнулся со странной проблемой при попытке документировать дескриптор Python. Следующее демонстрирует проблему. Мы определяем простой класс дескриптора noop и класс test с одним атрибутом, реализованным дескриптором noop. Класс дескриптора имеет строку документации. Затем мы проверяем, что отображается, когда help() запускается для различных вещей. Только help(noop) отображает строку документации, больше ничего не отображается, хотя поиск test.attr.__doc__ показывает ожидаемую строку. Это неожиданно.

Код: Выделить всё

class noop(object):
"""
XXX documentation.
"""

def __get__(self, obj, owner = None):
return self if obj is None else None

def __set__(self, obj, value):
pass

def __delete__(self, obj):
pass

class test(object):
attr = noop()

help(test)  # attr has no documentation
help(test.attr) # no documentation
print(test.attr.__doc__)        # prints "XXX documentation"
help(noop)  # shows "XXX documentation"
help(test())    # attr has no documentation
Во второй попытке мы добавляем к дескриптору метод .__init__() и устанавливаем атрибут экземпляра .__doc__. Теперь мы видим эту документацию при получении атрибута .attr либо из класса test, либо из экземпляра класса test, но нам показывается строка документации класса noop, когда мы просим о помощи. Ожидается, что различие будет.

Код: Выделить всё

#
# try again
#

class noop(object):
"""
XXX documentation.
"""
def __init__(self):
self.__doc__ = "YYY documentation."

def __get__(self, obj, owner = None):
return self if obj is None else None

def __set__(self, obj, value):
pass

def __delete__(self, obj):
pass

class test(object):
attr = noop()

help(test)  # shows "YYY documentation"
help(test.attr) # shows "YYY documentation"
help(noop)  # shows "XXX documentation"
help(test())    # shows "YYY documentation"
И здесь все становится странным. По причинам я хочу, чтобы во всех четырех случаях, описанных выше, мне была показана одна и та же документация. Я ожидал, что произойдет, если только класс noop определит атрибут .__doc__, если экземпляры класса не переопределят его, но этого не происходит. Итак, в третьей попытке я использую .__init__(), чтобы скопировать строку документации класса в атрибут .__doc__ экземпляра.

Код: Выделить всё

#
# OK, we get it, so let's do:
#

class noop(object):
"""
XXX documentation.
"""
def __init__(self):
print(noop.__doc__) # prints "XXX documentation."
self.__doc__ = noop.__doc__

def __get__(self, obj, owner = None):
return self if obj is None else None

def __set__(self, obj, value):
pass

def __delete__(self, obj):
pass

class test(object):
attr = noop()

help(test)  # attr has NO DOCUMENTATION
help(test.attr) # NO DOCUMENTATION
print(test.attr.__doc__)        # prints "XXX documentation"
help(noop)  # shows "XXX documentation"
help(test())    # attr has NO DOCUMENTATION
Это не работает.
Чтобы убедиться, что noop.__doc__ не пуст во время выполнения кода, я добавил оператор print() в метод .__init__(), и он печатает ожидаемую строку. Получение и печать атрибута .__doc__ экземпляра test.attr класса noop также показывает ожидаемую строку. Это подтверждает, что атрибут .__doc__ был правильно установлен методом .__init__(), но документация нам не показана. Изменение строки работает: self.__doc__ = noop.__doc__ + " ".
Вопросы:
  • Что происходит!? Почему Python отказывается отображать строку документации, о которой мы знаем?
  • Как же мне установить .__doc__ экземпляра равным .__doc__ класса? Является ли хак с добавлением одного пробельного символа серьезным решением!?
  • Зачем нам это вообще нужно? Когда кто-то извлекает атрибут из экземпляра класса, поиск проваливается до атрибута класса, если экземпляр не определяет атрибут с таким именем. В первом из трех приведенных выше примеров один оператор print() подтверждает, что именно это и происходит, когда .__doc__ извлекается из test.attr. Атрибут .__doc__ не является исключением из этого правила, так почему же нам не отображается строка документации класса, если экземпляр не определяет свой собственный .__doc__?


Подробнее здесь: https://stackoverflow.com/questions/798 ... escriptors
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «Python»