我如何使用预递增/递减操作符(++,——),就像在c++ ?

为什么++计数运行,但不改变变量的值?


当前回答

Python没有这些操作符,但如果你真的需要它们,你可以编写一个具有相同功能的函数。

def PreIncrement(name, local={}):
    #Equivalent to ++name
    if name in local:
        local[name]+=1
        return local[name]
    globals()[name]+=1
    return globals()[name]

def PostIncrement(name, local={}):
    #Equivalent to name++
    if name in local:
        local[name]+=1
        return local[name]-1
    globals()[name]+=1
    return globals()[name]-1

用法:

x = 1
y = PreIncrement('x') #y and x are both 2
a = 1
b = PostIncrement('a') #b is 1 and a is 2

在函数内部,如果你想改变局部变量,你必须添加locals()作为第二个参数,否则它将尝试改变全局变量。

x = 1
def test():
    x = 10
    y = PreIncrement('x') #y will be 2, local x will be still 10 and global x will be changed to 2
    z = PreIncrement('x', locals()) #z will be 11, local x will be 11 and global x will be unaltered
test()

还有这些函数,你可以做:

x = 1
print(PreIncrement('x'))   #print(x+=1) is illegal!

但在我看来,以下方法更清晰:

x = 1
x+=1
print(x)

递减运算符:

def PreDecrement(name, local={}):
    #Equivalent to --name
    if name in local:
        local[name]-=1
        return local[name]
    globals()[name]-=1
    return globals()[name]

def PostDecrement(name, local={}):
    #Equivalent to name--
    if name in local:
        local[name]-=1
        return local[name]+1
    globals()[name]-=1
    return globals()[name]+1

我使用这些函数在我的模块翻译javascript到python。

其他回答

是的,我也错过了++和-功能。几百万行c代码让这种想法在我的老头脑中根深蒂固,而不是与它斗争……这里是一个我拼凑起来实现的类:

pre- and post-increment, pre- and post-decrement, addition,
subtraction, multiplication, division, results assignable
as integer, printable, settable.

这里的是:

class counter(object):
    def __init__(self,v=0):
        self.set(v)

    def preinc(self):
        self.v += 1
        return self.v
    def predec(self):
        self.v -= 1
        return self.v

    def postinc(self):
        self.v += 1
        return self.v - 1
    def postdec(self):
        self.v -= 1
        return self.v + 1

    def __add__(self,addend):
        return self.v + addend
    def __sub__(self,subtrahend):
        return self.v - subtrahend
    def __mul__(self,multiplier):
        return self.v * multiplier
    def __div__(self,divisor):
        return self.v / divisor

    def __getitem__(self):
        return self.v

    def __str__(self):
        return str(self.v)

    def set(self,v):
        if type(v) != int:
            v = 0
        self.v = v

你可以这样使用它:

c = counter()                          # defaults to zero
for listItem in myList:                # imaginary task
     doSomething(c.postinc(),listItem) # passes c, but becomes c+1

...已经有了c,你可以这样做。

c.set(11)
while c.predec() > 0:
    print c

....或者只是……

d = counter(11)
while d.predec() > 0:
    print d

...和(重)赋值为整数…

c = counter(100)
d = c + 223 # assignment as integer
c = c + 223 # re-assignment as integer
print type(c),c # <type 'int'> 323

...而这将保持c作为类型计数器:

c = counter(100)
c.set(c + 223)
print type(c),c # <class '__main__.counter'> 323

编辑:

还有一点出乎意料(完全不受欢迎)的行为,

c = counter(42)
s = '%s: %d' % ('Expecting 42',c) # but getting non-numeric exception
print s

...因为在该元组中,没有使用getitem(),而是将对象的引用传递给格式化函数。叹息。所以:

c = counter(42)
s = '%s: %d' % ('Expecting 42',c.v) # and getting 42.
print s

...或者,更详细,更明确地说,我们实际上想要发生什么,尽管在实际形式中与冗长相反(使用c.v代替)……

c = counter(42)
s = '%s: %d' % ('Expecting 42',c.__getitem__()) # and getting 42.
print s

++不是运算符。它是两个+运算符。+运算符是单位运算符,它什么也不做。(澄清:+和-一元操作符仅适用于数字,但我假定您不会期望假设的++操作符适用于字符串。)

++count

解析为

+(+count)

翻译过来就是

count

你必须使用稍微长一点的+=运算符来做你想做的事情:

count += 1

我怀疑省略++和——操作符是为了保持一致性和简单性。我不知道Guido van Rossum为这个决定给出的确切理由,但我可以想象出一些理由:

Simpler parsing. Technically, parsing ++count is ambiguous, as it could be +, +, count (two unary + operators) just as easily as it could be ++, count (one unary ++ operator). It's not a significant syntactic ambiguity, but it does exist. Simpler language. ++ is nothing more than a synonym for += 1. It was a shorthand invented because C compilers were stupid and didn't know how to optimize a += 1 into the inc instruction most computers have. In this day of optimizing compilers and bytecode interpreted languages, adding operators to a language to allow programmers to optimize their code is usually frowned upon, especially in a language like Python that is designed to be consistent and readable. Confusing side-effects. One common newbie error in languages with ++ operators is mixing up the differences (both in precedence and in return value) between the pre- and post-increment/decrement operators, and Python likes to eliminate language "gotcha"-s. The precedence issues of pre-/post-increment in C are pretty hairy, and incredibly easy to mess up.

Python没有前增量和后增量操作符。

在Python中,整数是不可变的。那就是你不能改变他们。这是因为整数对象可以在多个名称下使用。试试这个:

>>> b = 5
>>> a = 5
>>> id(a)
162334512
>>> id(b)
162334512
>>> a is b
True

上面的A和b实际上是同一个物体。如果你增加a,你也会增加b,这不是你想要的。所以你必须重新分配。是这样的:

b = b + 1

许多使用python的C程序员都想要一个自增操作符,但是这个操作符看起来像是对对象进行了自增操作,而实际上是对对象进行了重赋。因此-=和+=运算符加在一起,比b = b+ 1更短,同时比b++更清晰和灵活,所以大多数人会用:

b += 1

将b重新赋值给b+1。这不是一个自增运算符,因为它不加b,而是重新赋值。

简而言之:Python在这里表现不同,因为它不是C语言,也不是机器代码的低级包装器,而是一种高级动态语言,其中增量没有意义,也不像C语言那样必要,例如,在C语言中,每次有循环时都要使用增量。

python中不像C语言中那样有后/前自增/自减操作符。

我们可以看到++或-作为多个符号相乘,就像我们在数学中做的(-1)*(-1)=(+1)。

E.g.

---count

解析为

-(-(-count)))

翻译过来就是

-(+count)

因为-号和-号的乘法是+

最后,

-count

扩展Henry的回答,我实验性地实现了一个语法糖库,实现了++:hdytto。

使用方法简单。从PyPI安装后,放置sitecustomize.py:

from hdytto import register_hdytto
register_hdytto()

在项目目录中。然后,使main.py:

# coding: hdytto

a = 5
print(a++)
print(++a)
b = 10 - --a
print(b--)

并通过PYTHONPATH=运行它。python main.py。输出将是

5
7
4

在解码脚本文件时,Hdytto将++替换为((a:=a+1)-1),因此它可以工作。