tipos sentencias iteraciones incremento for espaƱol dentro declarar como python operators increment decrement

sentencias - Comportamiento de los operadores de incremento y decremento en Python



sentencias en python (6)

En Python, una distinción entre expresiones y declaraciones se aplica rígidamente, en contraste con lenguajes como Common Lisp, Scheme o Ruby.

Wikipedia

Por lo tanto, al introducir dichos operadores, se rompería la expresión / división dividida.

Por la misma razón no puedes escribir

if x = 0: y = 1

como se puede en otros idiomas donde no se conserva tal distinción.

Observo que un operador de preincremento / decremento puede aplicarse a una variable (como ++count ). ¡Se compila, pero en realidad no cambia el valor de la variable!

¿Cuál es el comportamiento de los operadores de preincremento / decremento (++ / -) en Python?

¿Por qué Python se desvía del comportamiento de estos operadores vistos en C / C ++?


Cuando desea aumentar o disminuir, normalmente desea hacer eso en un entero. Al igual que:

b++

Pero en Python, los enteros son inmutables . Eso es que no puedes cambiarlos. Esto se debe a que los objetos enteros se pueden usar con varios nombres. Prueba esto:

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

A y B de arriba son en realidad el mismo objeto. Si incrementara a, también incrementaría b. Eso no es lo que quieres. Así que tienes que reasignar. Me gusta esto:

b = b + 1

O más simple:

b += 1

Lo cual reasignará b a b+1 . Eso no es un operador de incremento, porque no incrementa b , lo reasigna.

En resumen: Python se comporta de manera diferente aquí, porque no es C, y no es un envoltorio de bajo nivel alrededor del código de máquina, sino un lenguaje dinámico de alto nivel, donde los incrementos no tienen sentido, y tampoco son tan necesarios como en C , donde los usas cada vez que tienes un bucle, por ejemplo.


Mientras que las otras respuestas son correctas en la medida en que muestran lo que normalmente hace un mero + (es decir, dejar el número como está, si es uno), están incompletas en la medida en que no explican lo que sucede.

Para ser exactos, +x evalúa a x.__pos__() y ++x a x.__pos__().__pos__() .

Podría imaginar una estructura de clase MUY extraña (niños, ¡no hagan esto en casa!) Así:

class ValueKeeper(object): def __init__(self, value): self.value = value def __str__(self): return str(self.value) class A(ValueKeeper): def __pos__(self): print ''called A.__pos__'' return B(self.value - 3) class B(ValueKeeper): def __pos__(self): print ''called B.__pos__'' return A(self.value + 19) x = A(430) print x, type(x) print +x, type(+x) print ++x, type(++x) print +++x, type(+++x)


Python no tiene estos operadores, pero si realmente los necesita, puede escribir una función que tenga la misma funcionalidad.

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

Uso:

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

Dentro de una función, debe agregar locals () como segundo argumento si desea cambiar la variable local, de lo contrario intentará cambiar global.

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()

También con estas funciones puedes hacer:

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

Pero en mi opinión, el siguiente enfoque es mucho más claro:

x = 1 x+=1 print(x)

Operadores de decremento:

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

Utilicé estas funciones en mi módulo traduciendo javascript a python.


Sí, también me perdí la funcionalidad ++ y -. Unos pocos millones de líneas de código C grabaron ese tipo de pensamiento en mi cabeza anterior, y en lugar de combatirlo ... Aquí hay una clase que construí:

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

Aquí está:

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

Podrías usarlo así:

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

... ya teniendo c, podrías hacer esto ...

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

....o solo...

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

... y para (re) asignación en entero ...

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

... mientras esto mantendrá c como contador de tipo:

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

EDITAR:

Y luego está este poco de comportamiento inesperado (y completamente no deseado) ,

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

... porque dentro de esa tupla, getitem () no es lo que se usa, en cambio, se pasa una referencia al objeto a la función de formato. Suspiro. Asi que:

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

... o, más verbalmente, y explícitamente lo que realmente queríamos que sucediera, aunque está en contraposición en forma real por la verbosidad (use cv lugar) ...

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


++ no es un operador. Se trata de dos operadores + El operador + es el operador de identidad , que no hace nada. (Aclaración: los operadores + y - unarios solo funcionan con números, pero supongo que no esperaría que un operador hipotético ++ funcione con cadenas).

++count

Analiza como

+(+count)

Que se traduce en

count

Tienes que usar el operador ligeramente más largo += para hacer lo que quieres hacer:

count += 1

Sospecho que los operadores ++ y -- quedaron fuera por coherencia y simplicidad. No sé el argumento exacto que Guido van Rossum dio para la decisión, pero puedo imaginar algunos argumentos:

  • Análisis más sencillo. Técnicamente, analizar el ++count es ambiguo, ya que podría ser + , + , count (dos operadores unarios + ) con la misma facilidad que podría ser ++ , count (un operador unario ++ ). No es una ambigüedad sintáctica significativa, pero existe.
  • Lenguaje más sencillo. ++ no es más que un sinónimo para += 1 . Fue una taquigrafía inventada porque los compiladores de C eran estúpidos y no sabían cómo optimizar a += 1 en la instrucción inc tienen la mayoría de las computadoras. En este día de optimización de los compiladores y los lenguajes interpretados por el código de bytes, agregar operadores a un lenguaje para permitir que los programadores optimicen su código suele ser mal visto, especialmente en un lenguaje como Python que está diseñado para ser coherente y legible.
  • Efectos secundarios confusos. Un error de principiante común en lenguajes con operadores ++ es mezclar las diferencias (tanto en precedencia como en valor de retorno) entre los operadores pre y post incremento / decremento, y a Python le gusta eliminar el idioma "gotcha" -s. Los problemas de precedencia de pre- / post-incremento en C son bastante vellosos, y son increíblemente fáciles de desordenar.