Le langage Python (surtout les 3.x) permet de très générales déballage de iterables, un exemple simple de ce qui est
a, *rest = 1, 2, 3
Au fil des ans, ce déballage a été progressivement généralisée (voir, par exemple, PEP 3132 et PEP 448), lui permettant d'être utilisé dans de plus en plus de circonstances. Ainsi, j'ai été surpris de découvrir que le suivant n'est pas valide la syntaxe de Python 3.6 (et le reste en Python 3.7):
def f():
rest = [2, 3]
return 1, *rest # Invalid
Je peux le faire fonctionner en encapsulant le retour de tuple, entre parenthèses, comme ceci:
def f():
rest = [2, 3]
return (1, *rest) # Valid
Le fait que je l'utilise dans un return
déclaration semble être important, comme
t = 1, *rest
est en effet juridique et les résultats dans le même avec ou sans parenthèses.
Ont ce cas simplement été oublié par les développeurs Python, ou il y a aucune raison pour que ce cas n'est pas valide la syntaxe?
Pourquoi j'ai des soins
Cela rompt un contrat important, je pensais que j'avais avec le langage Python. Considérez les points suivants (valable aussi) solution:
def f():
rest = [2, 3]
t = 1, *rest
return t
Normalement, quand j'ai ce code, je considère t
être un nom temporaire, qui je devrais être en mesure de se débarrasser de tout simplement remplacer t
dans le bas de la ligne avec sa définition. Dans ce cas cependant, ce qui conduit au code non valide
def f():
rest = [2, 3]
return 1, *rest
Bien sûr, c'est pas une grosse affaire pour avoir à la place des parenthèses autour de la valeur de retour, mais généralement de nouvelles parenthèses ne sont nécessaires pour distinguer entre plusieurs résultats possibles (regroupement). Ici ce n'est pas le cas, comme en laissant de côté les parenthèses ne produit pas certains autres un comportement indésirable, mais plutôt pas de comportement à tous.