首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Python运算符重载和运算符结合性

Python运算符重载和运算符结合性
EN

Stack Overflow用户
提问于 2012-05-08 08:36:47
回答 2查看 912关注 0票数 5

我正在编写一个python程序,其中需要重载>>操作符。我面临的问题是,这个运算符需要是右关联的。因此,如果我执行以下操作

代码语言:javascript
复制
A >> B >> C >> D >> E

我希望这个代码被解析为

代码语言:javascript
复制
(A >> (B >> (C >> (D >> E))))

据我所知,在python中,这个运算符是左关联的,所以我会得到,

代码语言:javascript
复制
((((A >> B) >> C) >> D) >> E)

当你进行运算符重载时,有没有办法改变python中运算符的默认结合性?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2012-05-08 12:53:04

这可以是done...but,这将需要一些努力。基本思想是使用右移位操作符来创建和更新延迟实际计算的新类型的对象。

例如,假设上面的变量A、B、C、D和E都是Actual类型的对象。我们将引入一个由Actual的一个实例上的rshift操作生成的新类。Deferred还实现了rshift运算符,该运算符更新对象并返回自身。

(顺便说一句,对于这个答案的其余部分,我假设A、B、C、D和E是不可变的,并且rshift操作产生一个新对象。)

代码语言:javascript
复制
F = A >> B >> C >> D >> E

会是这样计算出来的。

代码语言:javascript
复制
F = Deferred(A,B) >> C >> D >> E
F = Deferred(A,B,C) >> D >> E
F = Deferred(A,B,C,D) >> E
F = Deferred(A,B,C,D,E)

F维护Actual的缓存实例,该实例是从反向序列计算得出的。此外,F实现了与Actual相同的接口,以便将在Deferred实例上调用的方法委托给Actual的缓存实例。

我不知道你在做的是什么类型的计算,所以在下面的例子中,我虚构了一些微不足道的东西,只是为了证明当实际执行延迟计算时,它们是相反的。

代码语言:javascript
复制
class Var(object):
    def __init__(self):
        pass

    @property
    def name(self):
        return self._name( )

    @property
    def length(self):
        return len(self.name)


class Actual(Var):
    def __init__(self, name):
        Var.__init__(self)
        self._text = name

    def _name(self):
        return self._text

    def __rshift__(self, other):
        if isinstance(other, Actual):
            return Deferred(self, other)

        return len(self.name)

    @staticmethod
    def NewFromShiftComputation(sequence):
        x = ' >> '.join(reversed(map(lambda actual: actual.name, sequence)))
        return Actual(x)



class Deferred(Var):
    def __init__(self, *args):
        Var.__init__(self)

        self._items  = [ ]
        self._actual = None  #-- cached "actual"

        for item in args:
            self._items.append(item)

    def _name(self):
        self._assure_actual( )
        return self._actual.name

    def __rshift__(self, other):
        self._actual = None  #-- Invalidate the cached "actual"
        self._items.append(other)
        return self

    def _assure_actual(self):
        if self._actual is None:
            self._actual = Actual.NewFromShiftComputation(self._items)



A = Actual('A')
B = Actual('B')
C = Actual('C')
D = Actual('D')
E = Actual('E')

F = A >> B >> C >> D >> E

print F.name
print F.length
票数 4
EN

Stack Overflow用户

发布于 2012-05-08 09:01:49

这不是操作员的问题。Python从左到右求值:

http://docs.python.org/reference/expressions.html#evaluation-order

因此,在这种情况下需要括号,因为它都是相同的运算符。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/10491006

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档