【问题标题】:How to change method calling order in python?如何在python中更改方法调用顺序?
【发布时间】:2013-05-10 17:06:44
【问题描述】:

我的问题是关于 python 中的运算符重载。我想设置方法在python中调用的“优先级”或“顺序”,我正在寻找一种pythonic方式来做到这一点。下面是一个非常离奇的例子,但我想它会告诉你重点。

假设我们要重载 python 中的__pos____call__ 运算符,以在复制和修改对象时制作语法糖。这是主要思想的虚拟实现:

import copy

class C(object):
    def __init__(self, **kwargs):
        self._set(**kwargs)

    def __call__(self, **kwargs):
        self._set(**kwargs)
        return(self)

    def __pos__(self):
        return(copy.deepcopy(self))

    def _set(self, **kwargs):
        for keyword, value in kwargs.iteritems():
            setattr(self, keyword, value)

# first case:
my_obj = C(a=12, b=33, c=55)
copied = +my_obj(b=77)
print vars(my_obj), vars(copied)
# >>> {'a': 12, 'c': 55, 'b': 77} {'a': 12, 'c': 55, 'b': 77}

# second case:
my_obj = C(a=12, b=33, c=55)
copied = (+my_obj)(b=77)
print vars(my_obj), vars(copied)
# >>> {'a': 12, 'c': 55, 'b': 33} {'a': 12, 'c': 55, 'b': 77}

现在,如您所见,在第一种情况下,首先调用 __call__ 方法,然后再调用 __pos__,因此修改了原始对象并复制了修改后的对象。我想要的结果是第二种情况,但首先我必须使用() 来区分先调用哪个方法,然后再调用哪个方法。

所以我的问题是:我怎样才能改变调用这些方法的顺序,可能在类中,而不用实例上的大括号分组运算符的调用?

提前致谢!

【问题讨论】:

    标签: python oop methods operator-overloading


    【解决方案1】:

    你不能,运算符优先级是内置在语言中的。我建议不要像这样重载运算符,它只会使编码器更难阅读。

    相反,我认为最好的选择是:

    copied = copy.deepcopy(my_obj)(b=77)
    

    (像这样使用__call__() 看起来也很奇怪,但根据场景可能有效。)

    【讨论】:

    • 场景非常简单:我正在构建一种“python-markup”语言,您将在其中定义结构层次结构和样式属性。所以写我上面提到的东西会很方便,因为在这种情况下,代码会更小,更容易阅读和编辑。在正常情况下,你是绝对正确的:显式优于隐式,我不会在我的基础代码中使用这些语法糖。
    • 我仍然认为这是一个坏主意。要么使用实际的 Python,要么使用自定义语言。否则,您最终会遇到这种奇怪的风格和目标组合。我也不同意缩短总是意味着更容易阅读和编辑。
    • 是的......好吧,词法分析器,解析器,编译器,附加库......这是很多工作,我以前做过,并且意识到:我真正想要的是标记的简单性和蟒蛇的力量。这就是我选择这个解决方案的原因..
    猜你喜欢
    • 1970-01-01
    • 2020-08-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-11-08
    • 2020-05-19
    • 1970-01-01
    相关资源
    最近更新 更多