web-dev-qa-db-fra.com

Comment implémenter l'infini en Java?

Est-ce que Java a quelque chose à représenter l'infini pour chaque type de données numérique? Comment est-il implémenté de telle sorte que je puisse faire des opérations mathématiques avec?

Par exemple.

int myInf = infinity; //However it is done
myInf + 5; //returns infinity
myInf*(-1); //returns negative infinity

J'ai essayé d'utiliser de très grands nombres, mais je veux une solution correcte, facile.

122
user1753100

double supporte Infinity

double inf = Double.POSITIVE_INFINITY;
System.out.println(inf + 5);
System.out.println(inf - inf); // same as Double.NaN
System.out.println(inf * -1); // same as Double.NEGATIVE_INFINITY

empreintes

Infinity
NaN
-Infinity

remarque: Infinity - Infinity est pas un nombre.

169
Peter Lawrey

Je suppose que vous utilisez un calcul mathématique entier pour une raison. Si tel est le cas, vous pouvez obtenir un résultat pratiquement identique à POSITIVE_INFINITY en utilisant le champ MAX_VALUE de la classe Integer:

Integer myInf = Integer.MAX_VALUE;

(Et pour NEGATIVE_INFINITY, vous pouvez utiliser MIN_VALUE.) Il y aura bien sûr quelques différences fonctionnelles, par exemple, lorsque l'on compare myInf à une valeur MAX_VALUE: ce nombre n'est évidemment pas inférieur à myInf .

Il y a aussi ne bibliothèque qui contient en fait les champs POSITIVE_INFINITY et NEGATIVE_INFINITY, mais ce ne sont en réalité que de nouveaux noms pour MAX_VALUE et MIN_VALUE.

30
JohnK

Pour utiliser Infinity, vous pouvez utiliser Double qui prend en charge Infinity: -

    System.out.println(Double.POSITIVE_INFINITY);
    System.out.println(Double.POSITIVE_INFINITY * -1);
    System.out.println(Double.NEGATIVE_INFINITY);

    System.out.println(Double.POSITIVE_INFINITY - Double.NEGATIVE_INFINITY);
    System.out.println(Double.POSITIVE_INFINITY - Double.POSITIVE_INFINITY);

OUTPUT: -

Infinity
-Infinity
-Infinity

Infinity 
NaN
11
Rohit Jain

Les types Double et Float ont la constante POSITIVE_INFINITY.

5
Tudor

Je ne suis pas sûr que Java ait l'infini pour chaque type numérique, mais pour certains types de données numériques, la réponse est positive:

Float.POSITIVE_INFINITY
Float.NEGATIVE_INFINITY

ou

Double.POSITIVE_INFINITY
Double.NEGATIVE_INFINITY

Vous pouvez également trouver utile l’article suivant, qui représente quelques opérations mathématiques impliquant +/- infini: Intricacies de nombres en virgule flottante Java .

4
Akos K

Seuls les types Double et Float prennent en charge POSITIVE_INFINITY constante.

3
NKM

Pour les types de wrapper numériques.

par exemple, Double.POSITVE_INFINITY

J'espère que cela pourrait vous aider.

2
Ankit HTech

Une solution générique consiste à introduire un nouveau type. Il est peut-être plus impliqué, mais il a l’avantage de fonctionner pour tout type qui ne définit pas son propre infini.

Si T est un type pour lequel lteq est défini, vous pouvez définir InfiniteOr<T> avec lteq à peu près comme ceci:

class InfiniteOr with type parameter T:
    field the_T of type null-or-an-actual-T
    isInfinite()
        return this.the_T == null
    getFinite():
        assert(!isInfinite());
        return this.the_T
    lteq(that)
        if that.isInfinite()
            return true
        if this.isInfinite()
            return false
        return this.getFinite().lteq(that.getFinite())

Je vous laisse le soin de traduire cela avec la syntaxe exacte Java. J'espère que les idées sont claires. mais laissez-moi les épeler quand même.

L'idée est de créer un nouveau type qui a toutes les mêmes valeurs qu'un type déjà existant, plus une valeur spéciale qui, autant que vous puissiez le savoir à l'aide de méthodes publiques, agit exactement de la manière dont vous souhaitez que l'infini agisse, par exemple. c'est plus que toute autre chose. J'utilise null pour représenter l'infini ici, car cela semble le plus simple en Java.

Si vous souhaitez ajouter des opérations arithmétiques, décidez ce qu'elles doivent faire, puis implémentez-les. C'est probablement plus simple si vous gérez d'abord les cas infinis, puis réutilisez les opérations existantes sur des valeurs finies du type d'origine.

Il peut y avoir ou non une tendance générale à décider s'il est avantageux ou non d'adopter une convention de traitement des infinis du côté gauche avant les infinis du côté droit ou inversement; Je ne saurais le dire sans l'essayer, mais pour des valeurs inférieures ou égales (lteq), je pense qu'il est plus simple de commencer par regarder l'infini du côté droit. Je remarque que lteq est pas commutatif, mais add et mul sont; c'est peut-être pertinent.

Remarque: il n'est pas toujours facile de définir avec exactitude ce qui devrait se passer pour des valeurs infinies. C'est pour la comparaison, l'addition et la multiplication, mais peut-être pas la soustraction. En outre, il existe une distinction entre nombres cardinaux et ordinaux infinis auxquels vous voudrez peut-être faire attention.

2
Jonas Kölker

Comme le numéro de classe n'est pas définitif, voici une idée que je ne trouve pas encore dans les autres articles. À savoir sous-classer le numéro de classe.

Cela fournirait en quelque sorte un objet qui peut être traité comme un infini pour Integer, Long, Double, Float, BigInteger et BigDecimal.

Comme il n'y a que deux valeurs, nous pourrions utiliser le modèle singleton:

public final class Infinity extends Number {
    public final static Infinity POSITIVE = new Infinity(false);
    public final static Infinity NEGATIVE = new Infinity(true);
    private boolean negative;
    private Infinity(boolean n) {
        negative = n;
    }
}

En quelque sorte, je pense que les méthodes restantes intValue (), longValue (), etc., devraient alors être remplacées pour générer une exception. Ainsi, la valeur de l'infini ne peut pas être utilisée sans précautions supplémentaires.

0