推荐学习书目
Learn Python the Hard Way
Python Sites
PyPI - Python Package Index
http://diveintopython.org/toc/index.html
Pocoo
值得关注的项目
PyPy
Celery
Jinja2
Read the Docs
gevent
pyenv
virtualenv
Stackless Python
Beautiful Soup
结巴中文分词
Green Unicorn
Sentry
Shovel
Pyflakes
pytest
Python 编程
pep8 Checker
Styles
PEP 8
Google Python Style Guide
Code Style from The Hitchhiker's Guide
fuxkcsdn
V2EX  ›  Python

有办法在 subclass 中修改 parent class 的方法,使其返回某个变量吗?( parent class 的该方法无返回值)

  •  
  •   fuxkcsdn · Jun 28, 2017 · 2622 views
    This topic created in 3288 days ago, the information mentioned may be changed or developed.

    代码大致如下,其中 parent class 是某个开源库类

    # parent class
    class A(object):
        # ... bala bala ...
        def test(self, url):
            # ... bala bala ...
            rsp = self.http.send(url=url)
            rsp = json.loads(rsp.content)
            self._session = self._session_type(rsp['a'], rsp['b'])
    
    # subclass
    class B(A):
        def test(self, url):
            # ... bala bala ...
            rsp = self.http.send(url=url)
            rsp = json.loads(rsp.content)
            self._session = self._session_type(rsp['a'], rsp['b'])
            self._xx = rsp['xx']
    

    如果 A.test 有将 rsp 返回的话,那 subclass 就只需要

    class B(A):
        def test(self, url):
            rsp = super(self.__class__, self).test(url)
            self._xx = rsp['xx']
    

    所以...是否有办法可以让 parent class 的 test 方法返回 rsp 呢?(排除修改 parent class 源码的方法)

    Supplement 1  ·  Jun 28, 2017

    2楼 的方法测试可行,实际代码片段测试,tracert 的覆盖方法会比复制父类代码的覆盖方法慢上9~10倍(timerit repeat number = 100000)

    import sys
    
    # parent class
    class A(object):
        # ... bala bala ...
        def test(self, url):
            # ... bala bala ...
            rsp = self.http.send(url=url)
            rsp = json.loads(rsp.content)
            self._session = self._session_type(rsp['a'], rsp['b'])
    
    # subclass
    class B(A):
        def test(self, url):
            _locals = {}
    
            def tracert(frame, event, arg):
                if event == 'return':
                    _locals.update(frame.f_locals.copy())
    
            sys.setprofile(tracert)
            
            try:
                super(self.__class__, self).test(url)
            finally:                       
                sys.setprofile(None)       
            rsp = _locals['rsp']
            self._xx = rsp['xx']
    
    6 replies    2017-06-29 07:41:59 +08:00
    douxie
        1
    douxie  
       Jun 28, 2017
    B 中的 test 重写一遍 A.test 的实现,不就行了么
    XYxe
        2
    XYxe  
       Jun 28, 2017   ❤️ 1
    你的问题是在函数执行结束后获取函数内的变量,一个可行的方法:
    Hzzone
        3
    Hzzone  
       Jun 28, 2017
    子类覆盖父类的方法...
    twistoy
        4
    twistoy  
       Jun 28, 2017
    重写一个函数,直接覆盖在 A.test 上面,似乎也可以?
    fuxkcsdn
        5
    fuxkcsdn  
    OP
       Jun 28, 2017
    @douxie
    @Hzzone
    我帖子里的例子代码不就是这样写了...因为父类的这方法代码挺多的,感觉复制一遍挺麻烦的...

    @XYxe
    可行,不过要覆盖的这方法挺常用的...这样弄的话挺影响执行效率的(测试了下,大概要慢 9~10 倍)...
    XYxe
        6
    XYxe  
       Jun 29, 2017
    @fuxkcsdn #5 肯定会慢啊。还有一个不一定可行的方法,修改 rsp=...之后调用的某个函数,例如这里的 self._session_type:



    这样效率不会有太大影响,但还是要复制一点父类的代码,如果有短一点的函数那可以考虑。
    About   ·   Help   ·   Advertise   ·   Blog   ·   API   ·   FAQ   ·   Solana   ·   1122 Online   Highest 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 101ms · UTC 17:56 · PVG 01:56 · LAX 10:56 · JFK 13:56
    ♥ Do have faith in what you're doing.