python oop 继承_oop-在Python中继承方法的文档字符串
oop-在Python中继承方法的文档字符串
我有一个带有文档字符串的OO层次结构,它需要与代码本身一样多的维护。 例如。,
class Swallow(object):
def airspeed(self):
"""Returns the airspeed (unladen)"""
raise NotImplementedError
class AfricanSwallow(Swallow):
def airspeed(self):
# whatever
现在,问题是_ask_arthur不继承超类方法的文档字符串。 我知道我可以使用模板方法模式来保留文档字符串,即
class Swallow(object):
def airspeed(self):
"""Returns the airspeed (unladen)"""
return self._ask_arthur()
并在每个子类中实现_ask_arthur。 但是,我想知道是否还有另一种方法来继承文档字符串,也许是我还没有发现的装饰器?
5个解决方案
23 votes
这是Paul McGuire的DocStringInheritor元类的变体。
如果子成员的文档字符串继承,则它会继承父成员的文档字符串docstring为空。
如果子类docstring为,它将继承父类docstring。空的。
它可以从以下任何类继承文档字符串任何基类的MRO,就像常规属性继承一样。
与类装饰器不同,元类是继承的,因此您只需要在某些顶级基类中设置一次元类,并且docstring继承将在整个OOP层次结构中发生。
import unittest
import sys
class DocStringInheritor(type):
"""
A variation on
http://groups.google.com/group/comp.lang.python/msg/26f7b4fcb4d66c95
by Paul McGuire
"""
def __new__(meta, name, bases, clsdict):
if not('__doc__' in clsdict and clsdict['__doc__']):
for mro_cls in (mro_cls for base in bases for mro_cls in base.mro()):
doc=mro_cls.__doc__
if doc:
clsdict['__doc__']=doc
break
for attr, attribute in clsdict.items():
if not attribute.__doc__:
for mro_cls in (mro_cls for base in bases for mro_cls in base.mro()
if hasattr(mro_cls, attr)):
doc=getattr(getattr(mro_cls,attr),'__doc__')
if doc:
if isinstance(attribute, property):
clsdict[attr] = property(attribute.fget, attribute.fset,
attribute.fdel, doc)
else:
attribute.__doc__ = doc
break
return type.__new__(meta, name, bases, clsdict)
class Test(unittest.TestCase):
def test_null(self):
class Foo(object):
def frobnicate(self): pass
class Bar(Foo, metaclass=DocStringInheritor):
pass
self.assertEqual(Bar.__doc__, object.__doc__)
self.assertEqual(Bar().__doc__, object.__doc__)
self.assertEqual(Bar.frobnicate.__doc__, None)
def test_inherit_from_parent(self):
class Foo(object):
'Foo'
def frobnicate(self):
'Frobnicate this gonk.'
class Bar(Foo, metaclass=DocStringInheritor):
pass
self.assertEqual(Foo.__doc__, 'Foo')
self.assertEqual(Foo().__doc__, 'Foo')
self.assertEqual(Bar.__doc__, 'Foo')
self.assertEqual(Bar().__doc__, 'Foo')
self.assertEqual(Bar.frobnicate.__doc__, 'Frobnicate this gonk.')
def test_inherit_from_mro(self):
class Foo(object):
'Foo'
def frobnicate(self):
'Frobnicate this gonk.'
class Bar(Foo):
pass
class Baz(Bar, metaclass=DocStringInheritor):
pass
self.assertEqual(Baz.__doc__, 'Foo')
self.assertEqual(Baz().__doc__, 'Foo')
self.assertEqual(Baz.frobnicate.__doc__, 'Frobnicate this gonk.')
def test_inherit_metaclass_(self):
class Foo(object):
'Foo'
def frobnicate(self):
'Frobnicate this gonk.'
class Bar(Foo, metaclass=DocStringInheritor):
pass
class Baz(Bar):
pass
self.assertEqual(Baz.__doc__, 'Foo')
self.assertEqual(Baz().__doc__, 'Foo')
self.assertEqual(Baz.frobnicate.__doc__, 'Frobnicate this gonk.')
def test_property(self):
class Foo(object):
@property
def frobnicate(self):
'Frobnicate this gonk.'
class Bar(Foo, metaclass=DocStringInheritor):
@property
def frobnicate(self): pass
self.assertEqual(Bar.frobnicate.__doc__, 'Frobnicate this gonk.')
if __name__ == '__main__':
sys.argv.insert(1, '--verbose')
unittest.main(argv=sys.argv)
unutbu answered 2020-01-27T02:02:29Z
22 votes
以类装饰器风格编写一个函数来为您执行复制。 在Python2.5中,您可以在创建类后直接应用它。 在更高版本中,您可以使用@decorator表示法。
这是如何做到的第一步:
import types
def fix_docs(cls):
for name, func in vars(cls).items():
if isinstance(func, types.FunctionType) and not func.__doc__:
print func, 'needs doc'
for parent in cls.__bases__:
parfunc = getattr(parent, name, None)
if parfunc and getattr(parfunc, '__doc__', None):
func.__doc__ = parfunc.__doc__
break
return cls
class Animal(object):
def walk(self):
'Walk like a duck'
class Dog(Animal):
def walk(self):
pass
Dog = fix_docs(Dog)
print Dog.walk.__doc__
在较新的Python版本中,最后一部分更加简单美观:
@fix_docs
class Dog(Animal):
def walk(self):
pass
这是一项Pythonic技术,与标准库中现有工具的设计完全匹配。 例如,functools.total_ordering类装饰器向类添加缺少的丰富比较方法。 再举一个例子,functools.wraps装饰器将元数据从一个函数复制到另一个函数。
Raymond Hettinger answered 2020-01-27T02:01:51Z
13 votes
仅供参考的FYY I人员:在Python 3.5上,inspection.getdoc自动从继承层次结构中检索文档字符串。
因此,上面的响应对于Python 2很有用,或者如果您想通过合并父母和孩子的文档字符串来变得更有创造力,那么它们很有用。
我还创建了一些用于文档字符串继承的轻量级工具。 这些支持开箱即用的一些不错的默认文档字符串样式(numpy,google,reST)。 您也可以轻松使用自己的文档字符串样式
Ryan Soklaski answered 2020-01-27T02:02:59Z
4 votes
以下适应还处理属性和mixin类。 我还遇到了不得不使用func.__func__(用于“实例方法”)的情况,但我不确定为什么其他解决方案不能解决这个问题。
def inherit_docs(cls):
for name in dir(cls):
func = getattr(cls, name)
if func.__doc__:
continue
for parent in cls.mro()[1:]:
if not hasattr(parent, name):
continue
doc = getattr(parent, name).__doc__
if not doc:
continue
try:
# __doc__'s of properties are read-only.
# The work-around below wraps the property into a new property.
if isinstance(func, property):
# We don't want to introduce new properties, therefore check
# if cls owns it or search where it's coming from.
# With that approach (using dir(cls) instead of var(cls))
# we also handle the mix-in class case.
wrapped = property(func.fget, func.fset, func.fdel, doc)
clss = filter(lambda c: name in vars(c).keys() and not getattr(c, name).__doc__, cls.mro())
setattr(clss[0], name, wrapped)
else:
try:
func = func.__func__ # for instancemethod's
except:
pass
func.__doc__ = doc
except: # some __doc__'s are not writable
pass
break
return cls
letmaik answered 2020-01-27T02:03:19Z
0 votes
def fix_docs(cls):
""" copies docstrings of derived attributes (methods, properties, attrs) from parent classes."""
public_undocumented_members = {name: func for name, func in vars(cls).items()
if not name.startswith('_') and not func.__doc__}
for name, func in public_undocumented_members.iteritems():
for parent in cls.mro()[1:]:
parfunc = getattr(parent, name, None)
if parfunc and getattr(parfunc, '__doc__', None):
if isinstance(func, property):
# copy property, since its doc attribute is read-only
new_prop = property(fget=func.fget, fset=func.fset,
fdel=func.fdel, doc=parfunc.__doc__)
cls.func = new_prop
else:
func.__doc__ = parfunc.__doc__
break
return cls
marscher answered 2020-01-27T02:03:35Z
python oop 继承_oop-在Python中继承方法的文档字符串相关推荐
- python html 语法高亮,在Python中使用doxygen样式文档字符串的Vim语法高亮显示
我开始使用doxygen来生成我的Python代码的文档. 我使用doxypy过滤器来预处理Python文档字符串. 我的目标是在Python中有一个很好的语法突出显示doxygen注释. 在专用.d ...
- python 生成html文件浏览器,pycharm中怎么生成HTML文档并在浏览器查看HTML文档
首先,介绍一下Python自带的pydoc模块,该模块能帮助我们生成以及查看HTML文档.(在控制台查看文档B格差了那么一丢丢,俺就没兴趣勒)待会能够熟练使用pydoc以后我们便可以直接在浏览器上打开 ...
- Python Tutorial中英双语对照文档5
Python Tutorial中英双语对照文档4 CHAPTER THIRTEEN WHAT NOW? 现在咧? Reading this tutorial has probably reinforc ...
- Python Tutorial中英双语对照文档3
接 Python Tutorial中英双语对照文档2 CHAPTER NINE CLASSES 类 Classes provide a means of bundling data and funct ...
- python中的文档字符串(docString)
python中的文档字符串(docString) - 泥土 - 博客园 python中的文档字符串(docString) Posted on 2009-02-19 15:27 泥土 阅读(2122) ...
- Python批量识别图片中的文字并保存到txt文档中
Python OCR工具pytesseract,之前是惠普的产品,被Google收了之后就给开源了. 1.需要下载并安装Google Tesseract,下载地址看图片上有,要下载4.0.0版本的 2 ...
- Python Tutorial中英双语对照文档1
本文根据官方文档 http://www.pythondoc.com/pythontutorial3/ 和 中文文档 http://www.pythondoc.com/pythontutorial3/ ...
- Python Tutorial中英双语对照文档2
接 Python Tutorial中英双语对照文档1 CHAPTER SIX MODULES 模块 If you quit from the Python interpreter and enter ...
- Python常用函数--文档字符串DocStrings
Python 有一个甚是优美的功能称作python文档字符串(Documentation Strings),在称呼它时通常会使用另一个短一些的名字docstrings.DocStrings 是一款你应 ...
最新文章
- 在SQL Server 2000 和SQL Server 2005中导出表结构
- bo a1 蓝牙音箱 中文说明
- C/C++ 为什么#ifndef 头文件 要用大写加下划线?(这就是一种约定俗成的规范)
- DispacherServlet默认加载配置文件名
- for..in..遍历循环的简写模式
- HOW TO:构造Java类
- 开机自启动脚本_使用xtu降低笔记本(游戏本)cpu电压及功耗·游戏本延时(以及试着解决开机自启动的问题)...
- Hemberg-lab单细胞转录组数据分析(三)
- PVLAN技术初探-巧用PVLAN优化网络
- mpi和openmp混合编程的优点_混合云:拥抱云计算的未来!
- RocketMQ 概述
- 怎么连接win10共享计算机,xp系统下怎么连接win10共享的打印机
- 全国海关分区图(含副厅)
- 图论(五)单源最短路算法
- 外贸软件常见图片类问题丨汇信
- 上行带宽,下行带宽和内网带宽的区别及相关问题
- 虚拟同步发电机_简报︱基于分散式微电网的虚拟同步发电机无通信预同步并网方案...
- 华为鸿蒙os的内核是Linux,谈华为鸿蒙内核和操作系统
- 我的第一份CUDA代码
- 基于多传感器的学生课堂掌握程度评估系统和方法
热门文章
- java List实体排序
- spark on yarn 使用自定义jdk
- 下图所示的PCB(进程控制块)的组织方式是(),图中()。【最全!最详细分析】
- 26行代码AC_试题 历届试题 日期问题 | 第八届蓝桥杯B组第七题
- Python去线性化趋势
- c语言30人成绩平均分,用C语言编程平均分数
- Docker相关概念与安装(Docker-CE)
- OpenStack(一)——OpenStack与云计算概述
- mysql 二进制转字符串_MySql字符转义 | 学步园
- python笔记之利用scrapy框架爬取糗事百科首页段子