18 votes

Définir la précision de sortie globale en Python

J'ai écrit une bibliothèque de fonctions pour rendre mes devoirs en ingénierie plus facile, et je les utilise dans l'interpréteur python (un peu comme une calculatrice). Certaines renvoient des matrices, d'autres renvoient des décimaux.

Le problème, c'est qu'elles renvoient trop de décimales. Par exemple, actuellement, lorsque un numéro est 0, je reçois un nombre extrêmement petit en retour (par exemple 6.123233995736766e-17)

Je sais comment formater les sorties individuellement, mais cela nécessiterait d'ajouter un formateur pour chaque ligne que je tape dans l'interpréteur. J'utilise python 2.6.

Y a-t-il un moyen de définir le format de sortie global (précision, etc...) pour la session ?

*Note : Pour les fonctions de scipy, je sais que je peux utiliser

scipy.set_printoptions(precision = 4, suppress = True)

mais cela ne semble pas fonctionner pour les fonctions qui n'utilisent pas scipy.

10voto

Blckknght Points 20780

Une idée serait d'ajouter from __future__ import print_function (en haut) puis de remplacer la fonction d'impression standard. Voici une implémentation très simple qui imprime les nombres flottants avec exactement deux chiffres après le point décimal :

def print(*args):
    __builtins__.print(*("%.2f" % a if isinstance(a, float) else a
                         for a in args))

Vous devriez mettre à jour votre code de sortie pour utiliser la fonction d'impression, mais au moins elle sera générique, plutôt que de nécessiter des règles de formatage personnalisées à chaque endroit. Si vous souhaitez modifier le fonctionnement du formatage, il vous suffit de changer la fonction print personnalisée.

10voto

Marc Points 721

Avec numpy, vous pourriez utiliser la méthode set_printoptions (http://docs.scipy.org/doc/numpy/reference/generated/numpy.set_printoptions.html).

Par exemple:

import numpy as np
np.set_printoptions(precision=4)
print(np.pi * np.arange(8))

8voto

Roland Smith Points 10392

Ce que vous voyez, c'est le fait que les nombres décimaux en virgule flottante ne peuvent être que approximés par des nombres en virgule flottante binaires. Voir Arithmétique en virgule flottante : Problèmes et Limitations.

Vous pouvez mettre une variable au niveau du module dans votre bibliothèque et l'utiliser comme deuxième paramètre de round() pour arrondir la valeur de retour des fonctions de votre module, mais c'est plutôt radical.

Si vous utilisez ipython (que je recommanderais pour une utilisation interactive, beaucoup mieux que l'interpréteur régulier), vous pouvez utiliser la fonction 'magique' %precision.

1voto

En s'appuyant sur la solution de @Blckknght, nous pourrions utiliser des regex pour quelque chose de plus robuste.

import re

round_to = 4

def str_round(match):
    return str(round(eval(match.group()), round_to))

def print(*args, **kwargs):
    if len(args):
        args = list(args)
        for i, text in enumerate(args):
        text = str(text)
        if re.search(r"([-+]?\d*\.?\d+|[-+]?\d+)", text):
            args[i] = re.sub(r"([-+]?\d*\.?\d+|[-+]?\d+)", str_round, text)

    return __builtins__.print(*args, **kwargs)

Maintenant, le nombre dans l'instruction d'impression suivante sera arrondi

>>> print(f"Le nombre {1/3} est dans cette phrase.")
Le nombre 0.3333 est dans cette phrase.

0voto

dstromberg Points 3126

Vous pourriez ajouter des méthodes str (en supposant que vous ne les avez pas déjà) pour vos résultats de nombres et de matrices, et les faire toujours utiliser le même .format ou %f.

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