Pourquoi Int32.TryParse réinitialise-t-il le paramètre out lorsqu’il est impossible de convertir?

si je lance ce code C #

int realInt = 3; ssortingng foo = "bar"; Int32.TryParse(foo, out realInt); Console.WriteLine(realInt); Console.Read(); 

Je reçois 0. Et j’aimerais savoir pourquoi! Parce que je ne peux trouver aucune raison pour cela. Cela me force à créer des variables temporaires pour chaque parsing. Donc s’il vous plait! Grands codeurs de l’univers, m’éclairer!

C’est “out”, pas “ref”. À l’intérieur de la méthode, il doit l’ assigner (sans la lire au préalable) pour satisfaire le sens du mot “out”.

En fait, “out” est une préoccupation de langage (et non de framework) – donc une implémentation gérée en C ++ pourrait probablement l’ignorer … mais il est plus cohérent de la suivre.

En réalité; si la méthode retourne false, vous ne devriez tout simplement pas regarder la valeur; Traitez-le comme un déchet jusqu’à ce qu’il soit assigné. Il est dit de retourner 0, mais c’est rarement utile.


Aussi – s’il ne l’a pas fait (c’est-à-dire s’il a préservé la valeur); que serait cette impression:

 int i; int.TryParse("gibber", out i); Console.WriteLine(i); 

C’est parfaitement valide C # … alors qu’est-ce qu’il imprime?

La doc Int32.TryParse Method (Ssortingng, Int32) indique:

Convertit la représentation sous forme de chaîne d’un nombre en son équivalent entier signé de 32 bits. Une valeur de retour indique si la conversion a réussi.

résultat

Type: System.Int32

Lorsque cette méthode retourne, contient la valeur entière signée sur 32 bits équivalente au nombre contenu dans s, si la conversion a réussi, ou à zéro si la conversion a échoué . La conversion échoue si le paramètre s est une référence null (rien dans Visual Basic), si son format n’est pas correct ou s’il représente un nombre inférieur à MinValue ou supérieur à MaxValue. Ce paramètre est passé non initialisé.

Comme le paramètre est un paramètre out, vous ne devez pas initialiser realInt lorsque vous le déclarez, car le compilateur peut voir que vous le transmettez à une méthode qui garantit de le définir à quelque chose (en raison du “out”). .

Maintenant, parce que c’est un paramètre de sortie, la TryParse est requirejse pour la définir. Il la met à 0 car c’est la valeur par défaut pour un int dans la plupart des situations en C #.

Vous pouvez l’écrire comme:

 int realInt; ssortingng foo="bar"; if(int.TryParse(foo,out realInt)==false) { realInt=3; } 

Parce que c’est ainsi que fonctionne le contrat “out”. Chaque fois que vous transmettez un paramètre de out à une fonction, c’est à la fonction de l’initialiser.

la documentation MSDN pour Int32.TryParse indique que si la conversion échoue, le résultat renvoie toujours 0.

Vous êtes généralement censé utiliser une variable de résultat temporaire, à savoir

 int value; bool succeeded = Int32.TryParse("assortingng", out value); if (succeeded) { // use value in some way } 

Ou vous emballez simplement la méthode complète dans une instruction if

 int value; if (Int32.TryParse("assortingng", out value)) { // use value in some way } 

Personnellement, je trouve que ce dernier est la meilleure option.

 public static class IntHelper { public static bool TryParse(ssortingng s, ref int outValue) { int newValue; bool ret = int.TryParse(s, out newValue); if (ret) outValue = newValue; return ret; } } 

Parce que (au moins en C #), la méthode qui prend un ou plusieurs parameters doit garantir qu’elle leur écrive. De cette façon, vous n’avez pas besoin d’initialiser les champs locaux d’une méthode avant de les transmettre en tant qu’arguments sortants à une méthode.

Je suppose que cela fait partie de la spécification C #:

10.5.1.3 Paramètres de sortie … Dans une méthode, tout comme une variable locale, un paramètre de sortie est considéré initialement> non affecté et doit être définitivement atsortingbué avant que sa valeur ne soit utilisée.

Chaque paramètre de sortie d’une méthode doit être définitivement atsortingbué avant le retour de la méthode.

Si tel est le cas, vous ne devriez pas vous fier à la valeur obtenue.

Le second paramètre de TryParse étant un paramètre out , la méthode TryParse est forcée pour l’initialiser. Si le paramètre avait été ref au lieu de out vous obtiendriez le comportement souhaité. Cependant, étant donné que la méthode TryParse n’a besoin que de générer un nombre et de ne recevoir aucun nombre, le paramètre approprié est le paramètre input.