Question

Le code suivant génère une erreur de compilation, telle que

.

Impossible de convertir le type 'chaîne' en 'int'

string name = Session["name1"].ToString();
int i = (int)name;

alors que le code ci-dessous est compilé et exécuté avec succès:

string name = Session["name1"].ToString();
int i = Convert.ToInt32(name);

je voudrais savoir:

  1. Pourquoi le premier code génère-t-il une erreur de compilation?

  2. Quelle est la différence entre les 2 extraits de code?

Était-ce utile?

La solution

(int) toto est simplement un transtypage vers le type Int32 ( int en C #). Ceci est intégré au CLR et requiert que toto soit une variable numérique (par exemple, float , long , etc.). En ce sens, très similaire à un casting en C.

Convert.ToInt32 est conçu pour être une fonction de conversion générale. Cela fait beaucoup plus que des castings; à savoir, il peut convertir n'importe quel type primitif en int (notamment en analysant une chaîne ). Vous pouvez voir la liste complète des surcharges de cette méthode ici sur MSDN .

Et comme Stefan Steiger mentionne dans un commentaire :

  

Notez également qu'au niveau numérique, (int) foo tronque foo ( ifoo = Math.Floor (foo) ), tandis que Convert.ToInt32 (foo) utilise moitié à arrondi (arrondit x.5 au nombre entier EVEN le plus proche, ce qui signifie ifoo = Math.Round (foo) ). Le résultat n’est donc pas seulement lié à la mise en œuvre, mais également pas au même nombre.

Autres conseils

(cette ligne concerne une question qui a été fusionnée) Vous ne devez jamais utiliser (int) someString - cela ne fonctionnera jamais (et le compilateur ne vous le laissera pas).

Cependant, int int.Parse (chaîne) et bool int.TryParse (chaîne, out int) (et leurs diverses surcharges) sont passables.

Personnellement, je principalement n’utilise que Convert pour les réflexions; mon choix est donc Analyser et . TryParse . La première est lorsque je m'attends à ce que la valeur soit un entier valide et que je veuille sinon une exception. La seconde est quand je veux vérifier s'il s'agit d'un entier valide. Je peux alors décider quoi faire quand il l'est / n'est pas.

Pour citer cette Article d'Eric Lippert :

  

Cast signifie deux choses contradictoires: "vérifiez si cet objet est vraiment de ce type, jetez-le s'il n'est pas". et "cet objet n'est pas du type donné; trouvez-moi une valeur équivalente qui appartient au type donné ".

Donc, ce que vous essayiez de faire en 1.) est d’affirmer que oui, String est un Int. Mais cette assertion échoue puisque String n’est pas un entier.

La raison 2.) réussie est due au fait que Convert.ToInt32 () analyse la chaîne et renvoie un int. Il peut toujours échouer, par exemple:

Convert.ToInt32("Hello");

Entraînerait une exception Argument.

En résumé, la conversion d'une chaîne en un entier est un problème de structure, et non quelque chose d'implicite dans le système de type .Net.

Une chaîne ne peut pas être convertie en un entier par diffusion explicite. Il doit être converti avec int.Parse .

Convert.ToInt32 encapsule fondamentalement cette méthode:

public static int ToInt32(string value)
{
    if (value == null)
    {
        return 0;
    }
    return int.Parse(value, CultureInfo.CurrentCulture);
}

Vous parlez d'une opération de diffusion C # avec des utilitaires de conversion .NET

  • C # Niveau de langue diffusion utilise des parenthèses - par exemple (int) - et la prise en charge de la conversion est limitée, car elle repose sur la compatibilité implicite entre les types ou sur des instructions explicitement définies par le développeur via opérateurs de conversion .
  • De nombreuses méthodes de conversion existent dans le .NET Framework, par exemple. System.Convert pour autoriser la conversion . strong> entre types de données identiques ou disparates.
La syntaxe

(Casting) fonctionne sur les types de données numériques, ainsi que sur "compatible". Types de données. Par types de données compatibles, il existe une relation établie par héritage (classes de base / dérivées) ou par implémentation (interfaces).

La diffusion peut également fonctionner entre différents types de données dont opérateurs de conversion définis.

La classe System.Convert , en revanche, est l’un des nombreux mécanismes disponibles pour convertir des éléments au sens général du terme. il contient une logique permettant de convertir entre des types de données disparates connus qui peuvent être modifiés logiquement d’un formulaire à un autre.

La conversion couvre même une partie du terrain de la diffusion en permettant la conversion entre des types de données similaires.

N'oubliez pas que le langage C # a sa propre façon de faire certaines choses.
Et le .NET Framework sous-jacent a sa propre façon de faire les choses, indépendamment de tout langage de programmation.
(Parfois, leurs intentions se chevauchent.)

Considérez le casting comme une fonctionnalité de niveau langage C # de nature plus limitée, et la conversion via la classe System.Convert comme l'un des nombreux mécanismes disponibles dans le framework .NET pour convertir des valeurs entre différents types.

Il n'y a pas de conversion par défaut de chaîne en int dans .NET. Vous pouvez utiliser int.Parse () ou int.TryParse () pour le faire. Vous pouvez également utiliser Convert.ToInt32 () comme vous l’avez fait.

Cependant, dans votre exemple, pourquoi faire un ToString () puis le reconvertir en int? Vous pouvez simplement stocker l’int dans Session et le récupérer comme suit:

int i = Session["name1"];

Juste un petit extra: dans différentes circonstances (par exemple, si vous convertissez un double, & c; en un Int32), vous pouvez également vous préoccuper de l'arrondi lorsque vous choisissez l'une ou l'autre de ces options. Convert.Int32 utilisera l'arrondi bancaire ( MSDN ); (int) sera simplement tronqué en un entier.

1) C # est un langage sûr et ne vous permet pas d'attribuer une chaîne à un nombre

2) la deuxième casse analyse la chaîne en nouvelle variable.  Dans votre cas, si la session est une session ASP.NET, il n’est pas nécessaire de stocker la chaîne et de la reconvertir lors de la récupération

.
int iVal = 5;
Session[Name1] = 5;
int iVal1 = (int)Session[Name1];

Convert.ToInt32

    return int.Parse(value, CultureInfo.CurrentCulture);

mais (int) est une transtypage de type, donc (int) "2" ne fonctionnera pas car vous ne pouvez pas lancer string en int. mais vous pouvez l’analyser comme Convert.ToInt32 do

La différence est que le premier extrait est une conversion et le second est un converti. Bien que, je pense que l’erreur du compilateur crée plus de confusion ici à cause de la formulation. Peut-être serait-il préférable de dire "Je ne peux pas transtyper le type 'chaîne' en 'int'.

Ceci est vieux, mais une autre différence est que (int) ne complète pas les nombres si vous avez un double ej: 5.7 la sortie utilisant (int) sera 5 et si vous utilisez Convert.ToInt () le nombre sera arrondi à 6.

Nous en avons déjà discuté, mais je souhaite partager un dialogue dotnet.

Si vous traitez avec des opérations arithmétiques et utilisez float, decimal, double, etc., vous devriez mieux utiliser Convert.ToInt32 ().

using System;

public class Program
{
  public static void Main()
  {
    double cost = 49.501;
    Console.WriteLine(Convert.ToInt32(cost));
    Console.WriteLine((int)cost);
  }
}

Sortie

50
49

https://dotnetfiddle.net/m3ddDQ

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top