• Empleos
  • Sobre nosotros
  • profesionales
    • Inicio
    • Empleos
    • Cursos y retos
    • Preguntas
    • Profesores
  • empresas
    • Inicio
    • Publicar vacante
    • Nuestro proceso
    • Precios
    • Pruebas Online
    • Nómina
    • Blog
    • Comercial
    • Calculadora de salario

0

180
Vistas
¿Cómo cambió print(*a, a.pop(0))?

Este código:

 a = [1, 2, 3] print(*a, a.pop(0))

Python 3.8 imprime 2 3 1 (hace el pop antes de desempacar).
Python 3.9 imprime 1 2 3 1 (aparece después de pop ).

¿Qué causó el cambio? No lo encontré en el registro de cambios .

Editar: no solo en las llamadas a funciones, sino también, por ejemplo, en una visualización de lista :

 a = [1, 2, 3] b = [*a, a.pop(0)] print(b)

Imprime [2, 3, 1] frente a [1, 2, 3, 1] . Y las listas de expresiones dicen "Las expresiones se evalúan de izquierda a derecha" (ese es el enlace a la documentación de Python 3.8), por lo que esperaría que la expresión de desempaquetado suceda primero.

about 3 years ago · Santiago Trujillo
1 Respuestas
Responde la pregunta

0

Sospecho que esto puede haber sido un accidente, aunque prefiero el nuevo comportamiento.

El nuevo comportamiento es consecuencia de un cambio en el funcionamiento del código de bytes para los argumentos * . El cambio está en el registro de cambios en Python 3.9.0 alfa 3:

bpo-39320 : Reemplace cuatro códigos de bytes complejos para construir secuencias con tres más simples.

Se han eliminado los siguientes cuatro bytecodes:

  • BUILD_LIST_UNPACK
  • BUILD_TUPLE_UNPACK
  • BUILD_SET_UNPACK
  • BUILD_TUPLE_UNPACK_WITH_CALL

Se han añadido los siguientes tres bytecodes:

  • LIST_TO_TUPLE
  • LIST_EXTEND
  • SET_UPDATE

En Python 3.8, el código de bytes para f(*a, a.pop()) se ve así:

 1 0 LOAD_NAME 0 (f) 2 LOAD_NAME 1 (a) 4 LOAD_NAME 1 (a) 6 LOAD_METHOD 2 (pop) 8 CALL_METHOD 0 10 BUILD_TUPLE 1 12 BUILD_TUPLE_UNPACK_WITH_CALL 2 14 CALL_FUNCTION_EX 0 16 RETURN_VALUE

mientras que en 3.9, se ve así:

 1 0 LOAD_NAME 0 (f) 2 BUILD_LIST 0 4 LOAD_NAME 1 (a) 6 LIST_EXTEND 1 8 LOAD_NAME 1 (a) 10 LOAD_METHOD 2 (pop) 12 CALL_METHOD 0 14 LIST_APPEND 1 16 LIST_TO_TUPLE 18 CALL_FUNCTION_EX 0 20 RETURN_VALUE

En el bytecode anterior, el código inserta a y (a.pop(),) en la pila, luego desempaqueta esos dos iterables en una tupla. En el nuevo código de bytes, el código inserta una lista en la pila, luego hace l.extend(a) y l.append(a.pop()) , luego llama a tuple(l) .

Este cambio tiene el efecto de cambiar el desempaquetado de a antes de la llamada pop , pero esto no parece haber sido deliberado. Mirando bpo-39320 , la intención era simplificar las instrucciones del código de bytes, no cambiar el comportamiento, y el subproceso bpo no tiene discusión sobre los cambios de comportamiento.

about 3 years ago · Santiago Trujillo Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Nuestro proceso Comercial
Legal
Términos y condiciones Política de privacidad
© 2025 PeakU Inc. All Rights Reserved.

Andres GPT

Recomiéndame algunas ofertas
Necesito ayuda