Qual è la differenza principale tra int.Parse () e Convert.ToInt32


492
  • Qual è la differenza principale tra int.Parse()e Convert.ToInt32()?
  • Quale deve essere preferito

Risposte:


448
  • Se hai una stringa e ti aspetti che sia sempre un numero intero (ad esempio, se un servizio Web ti sta consegnando un numero intero in formato stringa), utilizzeresti Int32.Parse().

  • Se stai raccogliendo input da un utente, in genere lo utilizzeresti Int32.TryParse(), poiché ti consente un controllo più approfondito sulla situazione quando l'utente immette input non validi.

  • Convert.ToInt32()prende un oggetto come argomento. (Vedi la risposta di Chris S per come funziona)

    Convert.ToInt32()inoltre non getta ArgumentNullExceptionquando il suo argomento è nullo come Int32.Parse()fa. Ciò significa anche che Convert.ToInt32()probabilmente è un po 'più lento di Int32.Parse(), sebbene in pratica, a meno che non si stia eseguendo un numero molto elevato di iterazioni in un ciclo, non lo noterai mai.


54
Come altri sottolineano, Convert.ToInt32 (s) non genera un'eccezione quando s è null, ma Parse () lo fa. "Un po 'più lento" è completamente accanto al punto in quanto non misurerai mai la differenza.
Robert Paulson,

4
Grazie Robert! Sto modificando la mia risposta per un po 'più di completezza. Ma per quanto riguarda le prestazioni, scommetto che la differenza di velocità sarebbe rilevabile se la chiami in un ciclo annidato ...
Dave Markle,

5
In realtà, poiché il ToInt32metodo ha un sovraccarico per un sacco di tipi, lì tra loro System.String, non si perde tempo a discernere il tipo. Il codice effettivo non fa altro che restituire 0 per valori null e int.Parse(value, CultureInfo.CurrentCulture)per tutto il resto.
Andreas Eriksson,

6
@StealthRabbi: Nella sezione "Valore restituito" della documentazione: "Un numero intero con
Dave Markle,

3
rimuovi la tua menzione di Int32.TryParse()in Convert.ToInt32()perché non è corretta. Convert genera un'eccezione se la stringa è formattata in modo errato.
Dehalion,

191

Dai un'occhiata al riflettore:

int.Parse ( "32"):

public static int Parse(string s)
{
    return System.Number.ParseInt32(s, NumberStyles.Integer, NumberFormatInfo.CurrentInfo);
}

che è una chiamata a:

internal static unsafe int ParseInt32(string s, NumberStyles style, NumberFormatInfo info)
{
    byte* stackBuffer = stackalloc byte[1 * 0x72];
    NumberBuffer number = new NumberBuffer(stackBuffer);
    int num = 0;
    StringToNumber(s, style, ref number, info, false);
    if ((style & NumberStyles.AllowHexSpecifier) != NumberStyles.None)
    {
        if (!HexNumberToInt32(ref number, ref num))
        {
            throw new OverflowException(Environment.GetResourceString("Overflow_Int32"));
        }
        return num;
    }
    if (!NumberToInt32(ref number, ref num))
    {
        throw new OverflowException(Environment.GetResourceString("Overflow_Int32"));
    }
    return num;
}

Convert.ToInt32 ( "32"):

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

Come dice il primo commento (di Dave M).


19
Grazie per aver rimosso tutte le congetture dalla risposta precedente.
bopapa_1979,

1
non dovrebbe essere "return default (int);" ?
Skorunka František,

2
In breve, Convert.ToInt32restituisce 0se nullper impedire int.Parsedi aumentare un ArgumentNullException.
André Leria,

4
@ SkorunkaFrantišek - L'espressione default(int)viene valutata in fase di compilazione, poiché è un valore intrinseco - il risultato dell'espressione è 0, quindi il compilatore inserisce un valore letterale 0. Gli strumenti di disassemblaggio IL non possono sapere di meglio, quindi ti mostrano solo uno zero letterale.
antiduh,

4
@ SkorunkaFrantišek Questo è del tutto oltre il punto. L'utente stava copiando il codice riflesso. Modificarlo sarebbe una rappresentazione errata di ciò che viene compilato. Se l'utente avesse l'origine originale e l'origine originale fosse predefinita (int), questo sarebbe ciò che l'utente avrebbe pubblicato.
rshadman,

78

Nessuna differenza in quanto tale.
Convert.ToInt32()chiama int.Parse()internamente

Tranne una cosa Convert.ToInt32()ritorna 0quando l'argomento ènull

Altrimenti funzionano entrambi allo stesso modo


5
Più precisamente, Convert.ToInt32(string)chiama int.Parseinternamente.Convert.ToInt32(object), tuttavia, le chiamate ((IConvertible) value).ToInt32, che nel caso delle stringchiamate Convert.ToInt32(string)... un po 'contorte ...
Timwi,

3
Sì, Convert.ToInt32 (char) restituirà effettivamente il valore (int), che trasformerà '1' in 49. Non generalmente la funzionalità prevista.
Dale K,

32

int.Parse (stringhe)

  • Numero intero in GAMMA> restituisce il valore intero
  • Valore nullo> ArguementNullException
  • Non in formato> FormatException
  • Valore non in RANGE> OverflowException

Convert.ToInt32 (stringhe)

  • Numero intero in GAMMA> restituisce il valore intero
  • Valore nullo> restituisce "0"
  • Non in formato> FormatException
  • Valore non in RANGE> OverflowException

bool isParsed = int. TryParse (string s, out res)

  • Intero in RANGE> restituisce valore intero, isParsed = true
  • Valore nullo> restituisce "0", isParsed = false
  • Non in formato> restituisce "0", isParsed = false
  • Il valore non è in RANGE> restituisce "0", isParsed = false

Prova questo codice qui sotto .....

class Program
{
    static void Main(string[] args)
    {
        string strInt = "24532";
        string strNull = null;
        string strWrongFrmt = "5.87";
        string strAboveRange = "98765432123456";
        int res;
        try
        {
            // int.Parse() - TEST
            res = int.Parse(strInt); // res = 24532
            res = int.Parse(strNull); // System.ArgumentNullException
            res = int.Parse(strWrongFrmt); // System.FormatException
            res = int.Parse(strAboveRange); // System.OverflowException

            // Convert.ToInt32(string s) - TEST
            res = Convert.ToInt32(strInt); // res = 24532
            res = Convert.ToInt32(strNull); // res = 0
            res = Convert.ToInt32(strWrongFrmt); // System.FormatException
            res = Convert.ToInt32(strAboveRange); //System.OverflowException

            // int.TryParse(string s, out res) - Test
            bool isParsed;
            isParsed = int.TryParse(strInt, out res); // isParsed = true, res = 24532
            isParsed = int.TryParse(strNull, out res); // isParsed = false, res = 0
            isParsed = int.TryParse(strWrongFrmt, out res); // isParsed = false, res = 0
            isParsed = int.TryParse(strAboveRange, out res); // isParsed = false, res = 0 
        }
        catch(Exception e)
        {
            Console.WriteLine("Check this.\n" + e.Message);
        }
    }


22

La differenza è questa:

Int32.Parse()e Int32.TryParse()può solo convertire stringhe. Convert.ToInt32()può prendere qualsiasi classe che implementa IConvertible. Se gli passi una stringa, allora sono equivalenti, tranne per il fatto che hai un sovraccarico extra per i confronti dei tipi, ecc. Se stai convertendo le stringhe, TryParse()probabilmente è l'opzione migliore.


9

Int32.Parse (stringa) --->

Il metodo Int32.Parse (string s) converte la rappresentazione di stringa di un numero nel suo equivalente intero con segno a 32 bit. Quando s è riferimento null, genererà ArgumentNullException. Se s è diverso dal valore intero, genererà FormatException. Quando s rappresenta un numero inferiore a MinValue o maggiore di MaxValue, genererà OverflowException. Per esempio :

string s1 = "1234"; 
string s2 = "1234.65"; 
string s3 = null; 
string s4 = "123456789123456789123456789123456789123456789"; 

result = Int32.Parse(s1);    //1234
result = Int32.Parse(s2);    //FormatException
result = Int32.Parse(s3);    //ArgumentNullException 
result = Int32.Parse(s4);    //OverflowException

Convert.ToInt32 (stringa) -> Metodo Convert.ToInt32 (stringa) converte la rappresentazione di stringa specificata dell'equivalente intero con segno a 32 bit. Questo chiama a sua volta il metodo Int32.Parse (). Quando s è un riferimento null, restituirà 0 invece di lanciare ArgumentNullException. Se s è diverso dal valore intero, genererà FormatException. Quando s rappresenta un numero inferiore a MinValue o maggiore di MaxValue, genererà OverflowException.

Per esempio:

 result = Convert.ToInt32(s1);    // 1234 
 result = Convert.ToInt32(s2);    // FormatException
 result = Convert.ToInt32(s3);    // 0
 result = Convert.ToInt32(s4);    // OverflowException 

1
aggiungi riferimento: codeproject.com/Articles/32885/…
T.Todua

8

TryParse è più veloce ...

La prima di queste funzioni, Parse, è quella che dovrebbe essere familiare a qualsiasi sviluppatore .Net. Questa funzione prenderà una stringa e tenterà di estrarne un intero e quindi restituirà l'intero. Se si imbatte in qualcosa che non può analizzare, genera una FormatException o se il numero è troppo grande una OverflowException. Inoltre, può generare ArgumentException se gli passa un valore null.

TryParse è una nuova aggiunta al nuovo framework .Net 2.0 che risolve alcuni problemi con la funzione Parse originale. La differenza principale è che la gestione delle eccezioni è molto lenta, quindi se TryParse non è in grado di analizzare la stringa non genera un'eccezione come Parse. Al contrario, restituisce un valore booleano che indica se è stato in grado di analizzare correttamente un numero. Quindi devi passare a TryParse sia la stringa da analizzare sia un parametro Int32 out da compilare. Useremo il profiler per esaminare la differenza di velocità tra TryParse e Parse in entrambi i casi in cui la stringa può essere analizzata correttamente e nei casi in cui la stringa non può essere analizzata correttamente.

La classe Convert contiene una serie di funzioni per convertire una classe base in un'altra. Credo che Convert.ToInt32 (stringa) controlli solo una stringa nulla (se la stringa è nulla restituisce zero a differenza del Parse), quindi chiama solo Int32.Parse (stringa). Userò il profiler per confermare questo e per vedere se l'uso di Convert invece di Parse ha effetti reali sulle prestazioni.

Fonte con esempi

Spero che sia di aiuto.


3
Quando guardi la fonte da TryParse in realtà non ha alcuna eccezione nella gestione - solo manipolazione dei personaggi e spostamento dei bit, grazie per il link
Chris S

2
Secondo questi benchmark , Parse, TryParse e Convert hanno praticamente la stessa velocità a meno che non si stiano convertendo più di 2 milioni di oggetti.
Coder gratuito 24

4
Convert.ToInt32

ha 19 sovraccarichi o 19 modi diversi che puoi chiamarlo. Forse di più nelle versioni del 2010.

Tenterà di convertire dai seguenti TIPI;

Oggetto, Booleano, Char, SByte, Byte, Int16, UInt16, Int32, UInt32, Int64, UInt64, Single, Double, Decimal, String, Date

e ha anche una serie di altri metodi; uno a che fare con una base numerica e 2 metodi prevedono aSystem.IFormatProvider

Parse invece ha solo 4 sovraccarichi o 4 modi diversi per chiamare il metodo.

Integer.Parse( s As String)

Integer.Parse( s As String,  style As System.Globalization.NumberStyles )

Integer.Parse( s As String, provider As System.IFormatProvider )

Integer.Parse( s As String,  style As System.Globalization.NumberStyles, provider As System.IFormatProvider )

2

Dipende dal tipo di parametro. Ad esempio, ho appena scoperto oggi che convertirà un carattere direttamente in int usando il suo valore ASCII. Non esattamente la funzionalità che intendevo ...

SEI STATO AVVERTITO!

public static int ToInt32(char value)
{
    return (int)value;
} 

Convert.ToInt32('1'); // Returns 49
int.Parse('1'); // Returns 1

Può charconvertire implicitamente in stringin C #? Certamente può farlo in VB.NET, e quindi i programmatori in quella lingua probabilmente si aspetterebbero Convert.ToInt32("1"c)e Convert.ToInt32("1")saranno equivalenti, ma non credo che C # abbia quella conversione implicita.
supercat,

Non è possibile convertire char in string, implicitamente o esplicitamente. Dovresti chiamare '1'.ToString () o nuova stringa (' 1 ', 1);
Dale K,

3
Non considererei questo "avvertimento" terribilmente significativo per C #, dato che quel linguaggio considera i charvalori un po 'più numerici di vb.net. Il pericolo sarebbe maggiore in vb.net, dove a causa di un cast implicito c'è meno differenza percepita tra Chare String.
supercat

2

Ecco un dettaglio per int.Parsee Convert.ToInt32: supponiamo che tu abbia un array di caratteri char[] a=['1','2','3','4']e desideri convertire ogni elemento in un numero intero. Il Convert.ToInt32(a[0])vi darà un numero di 49. Si tratta come codice ASCII L' int.Parse(a[0])vi darà l'uscita a destra che è 1

Se si dispone di un array di stringhe string[] b=['1','2','3','4'], quindi Convert.ToInt32e int.Parsenon avrà alcuna differenza nell'output. Entrambi restituiscono il numero intero giusto.


1

Convert.ToInt32 consente un valore null, non genera alcun errore Int.parse non consente un valore null, genera un errore ArgumentNullException.


1

per chiarimenti applicazione console aperta, basta copiare il codice qui sotto e incollarlo nel static void Main(string[] args)metodo, spero che tu possa capire

public  class Program
    {
        static void Main(string[] args)
        { 
            int result;
            bool status;
            string s1 = "12345";
            Console.WriteLine("input1:12345");
            string s2 = "1234.45";
            Console.WriteLine("input2:1234.45");
            string s3 = null;
            Console.WriteLine("input3:null");
            string s4 = "1234567899012345677890123456789012345667890";
            Console.WriteLine("input4:1234567899012345677890123456789012345667890");
            string s5 = string.Empty;
            Console.WriteLine("input5:String.Empty");
            Console.WriteLine();
            Console.WriteLine("--------Int.Parse Methods Outputs-------------");
            try
            {
               result = int.Parse(s1);

               Console.WriteLine("OutPut1:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut1:"+ee.Message);
            }
            try
            {
              result = int.Parse(s2);

              Console.WriteLine("OutPut2:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut2:" + ee.Message);
            }
            try
            {
               result = int.Parse(s3);

               Console.WriteLine("OutPut3:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut3:" + ee.Message);
            }
            try
            {
                result = int.Parse(s4);

                Console.WriteLine("OutPut4:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut4:" + ee.Message);
            }

            try
            {
                 result = int.Parse(s5);

                 Console.WriteLine("OutPut5:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut5:" + ee.Message);
            }
            Console.WriteLine();
            Console.WriteLine("--------Convert.To.Int32 Method Outputs-------------");
            try
            {

                result=  Convert.ToInt32(s1);

                Console.WriteLine("OutPut1:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut1:" + ee.Message);
            }
            try
            {

                result = Convert.ToInt32(s2);

                Console.WriteLine("OutPut2:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut2:" + ee.Message);
            }
            try
            {

         result = Convert.ToInt32(s3);

         Console.WriteLine("OutPut3:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut3:" + ee.Message);
            }
            try
            {

                  result = Convert.ToInt32(s4);

                  Console.WriteLine("OutPut4:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut4:" + ee.Message);
            }

            try
            {

                 result = Convert.ToInt32(s5);

                 Console.WriteLine("OutPut5:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut5:" + ee.Message);
            }

            Console.WriteLine();
            Console.WriteLine("--------TryParse Methods Outputs-------------");
            try
            {

                status = int.TryParse(s1, out result);
                Console.WriteLine("OutPut1:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut1:" + ee.Message);
            }
            try
            {

                status = int.TryParse(s2, out result);
                Console.WriteLine("OutPut2:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut2:" + ee.Message);
            }
            try
            {

                status = int.TryParse(s3, out result);
                Console.WriteLine("OutPut3:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut3:" + ee.Message);
            }
            try
            {

                status = int.TryParse(s4, out result);
                Console.WriteLine("OutPut4:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut4:" + ee.Message);
            }

            try
            {

                status = int.TryParse(s5, out result);
                Console.WriteLine("OutPut5:" + result);
            }
            catch (Exception ee)
            {
                Console.WriteLine("OutPut5:" + ee.Message);
            }


            Console.Read();
        }
    }

1

I metodi Parse () forniscono gli stili numerici che non possono essere utilizzati per Convert (). Per esempio:

int i;
bool b = int.TryParse( "123-",
           System.Globalization.NumberStyles.AllowTrailingSign,
           System.Globalization.CultureInfo.InvariantCulture,
           out i);

analizzerebbe i numeri con il segno finale in modo che i == -123
Il segno finale sia popolare nei sistemi ERP.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.