64 votes

mypy, type hint : Union [float, int] -> existe-t-il un type Number ?

Mypy est vraiment pratique et corrige beaucoup de bogues, mais lorsque j'écris des applications "scientifiques", je finis souvent par le faire :

def my_func(number: Union[float, int]):
    # Do something

number est soit un float, soit un int, selon l'entrée de l'utilisateur. Existe-t-il un moyen officiel de faire cela ?

103voto

Martijn Pieters Points 271458

Utilisez float uniquement comme int est implicite dans ce type :

def my_func(number: float):

PEP 484 Conseils sur les types stipule spécifiquement que :

Plutôt que d'exiger que les utilisateurs écrivent des numéros d'importation et utilisent ensuite numbers.Float etc., ce PEP propose un raccourci simple et presque aussi efficace : lorsqu'un argument est annoté comme ayant le type float un argument de type int est acceptable ; de même, pour un argument annoté comme ayant le type complexe, les arguments de type float ou int sont acceptables.

(C'est moi qui souligne en gras).

Idéalement, vous devriez toujours utiliser numbers.Real :

from numbers import Real

def my_func(number: Real):

car cela permettrait d'accepter fractions.Fraction() y decimal.Decimal() La pyramide des nombres ne se limite pas aux nombres entiers et aux valeurs à virgule flottante.

Cependant, ces derniers ne fonctionnent pas actuellement lorsque l'on utilise mypy pour effectuer votre vérification de type, voir Mypy #3186 .

4 votes

Tangentiellement lié, mais Decimal n'est pas réellement une sous-classe de Real ou une partie de la tour numérique : python.org/dev/peps/pep-3141/#the-decimal-type

1voto

Curt Welch Points 101

Vous pouvez définir votre propre type pour résoudre ce problème et garder votre code plus propre.

FloatInt = Union[float, int]

def my_func(number: FloatInt):
    # Do something

0voto

patapouf_ai Points 6350

Pour les personnes qui viennent à cette question pour le problème plus général des indices de typage de l'Union pour des entités qui n'ont pas de supertype existant en commun, par exemple Union[int, numpy.ndarray] la solution est d'importer Union de typing .

Exemple 1 :

from typing import Union

def my_func(number: Union[float, int]):
    # Do something

Exemple 2 :

from typing import Union
import numpy as np

def my_func(x: Union[float, np.ndarray]):
    # do something
    # Do something

0voto

Trying2Learn Points 11

Python > 3.10 vous permet de faire ce qui suit.

def my_func(number: int | float) -> int | float:

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X