Tipi numerici integrali (Riferimenti per C#)
I tipi numerici integrali rappresentano numeri interi. Tutti i tipi numerici integrali sono tipi valore. Sono anche tipi semplici e possono essere inizializzati con valori letterali. Tutti i tipi numerici integrali supportano gli operatori aritmetici, logici bit per bit, di confronto e di uguaglianza.
Caratteristiche dei tipi integrali
C# supporta i tipi integrali predefiniti seguenti:
Tipo/parola chiave C# | Intervallo | Dimensione | Tipo .NET |
---|---|---|---|
sbyte |
Da -128 a 127 | Valore intero con segno a 8 bit | System.SByte |
byte |
da 0 a 255 | Intero senza segno a 8 bit | System.Byte |
short |
Da -32.768 a 32.767 | Valore intero a 16 bit con segno | System.Int16 |
ushort |
Da 0 a 65.535 | Intero senza segno a 16 bit | System.UInt16 |
int |
Da -2.147.483.648 a 2.147.483.647 | Valore intero a 32 bit con segno | System.Int32 |
uint |
Da 0 a 4.294.967.295 | Intero senza segno a 32 bit | System.UInt32 |
long |
Da -9.223.372.036.854.775.808 a 9.223.372.036.854.775.807 | Valore intero a 64 bit con segno | System.Int64 |
ulong |
Da 0 a 18.446.744.073.709.551.615 | Intero senza segno a 64 bit | System.UInt64 |
nint |
Dipende dalla piattaforma (calcolata in fase di esecuzione) | Intero con segno a 32 bit o a 64 bit | System.IntPtr |
nuint |
Dipende dalla piattaforma (calcolata in fase di esecuzione) | Intero senza segno a 32 bit o a 64 bit | System.UIntPtr |
In tutte le righe della tabella, ad eccezione delle ultime due, ogni parola chiave di tipo C# dalla colonna all'estrema sinistra è un alias per il tipo .NET corrispondente. La parola chiave e il nome del tipo .NET sono intercambiabili. Ad esempio, le dichiarazioni seguenti dichiarano variabili dello stesso tipo:
int a = 123;
System.Int32 b = 123;
I tipi nint
e nuint
nelle ultime due righe della tabella sono numeri interi di dimensioni native. È possibile usare le parole chiave contestuali nint
e nuint
per definire interi di dimensioni native. Questi sono numeri interi a 32 bit quando vengono eseguiti in un processo a 32 bit o interi a 64 bit quando vengono eseguiti in un processo a 64 bit. Possono essere usati per scenari di interoperabilità, librerie di basso livello e per ottimizzare le prestazioni negli scenari in cui la matematica Integer viene usata ampiamente.
I tipi Integer di dimensioni native vengono rappresentati internamente come tipi .NET System.IntPtr e System.UIntPtr. A partire da C# 11, i tipi nint
e nuint
sono alias per i tipi sottostanti.
Il valore predefinito di ogni tipo integrale è zero 0
.
Ogni tipo integrale ha costanti MinValue
e MaxValue
che specificano il valore minimo e massimo del tipo. Queste proprietà sono costanti in fase di compilazione, ad eccezione del caso dei tipi di dimensioni native (nint
e nuint
). Le proprietà MinValue
e MaxValue
vengono calcolate in fase di esecuzione per i tipi di dimensioni native. Le dimensioni di questi tipi dipendono dalle impostazioni del processo.
Usare la struttura System.Numerics.BigInteger per rappresentare un intero con segno senza limiti inferiori o superiori.
Valori letterali Integer
I valori letterali Integer possono essere
- decimali: senza prefisso
- esadecimali: con il prefisso
0x
o0X
- binari: con il prefisso
0b
o0B
Il codice seguente illustra un esempio di ognuno di essi:
var decimalLiteral = 42;
var hexLiteral = 0x2A;
var binaryLiteral = 0b_0010_1010;
L'esempio precedente mostra anche l'uso di _
come separatore di cifre. È possibile usare il separatore di cifre con tutti i tipi di valori letterali numerici.
Il tipo di un valore letterale intero è determinato dal relativo suffisso come indicato di seguito:
Se un valore letterale intero non ha alcun suffisso, il suo tipo corrisponderà al primo dei tipi seguenti in cui il suo valore può essere rappresentato:
int
,uint
,long
,ulong
.Nota
I valori letterali vengono interpretati come valori positivi. Ad esempio, il valore letterale
0xFF_FF_FF_FF
rappresenta il numero4294967295
deluint
tipo, anche se ha la stessa rappresentazione bit del numero-1
del tipoint
. Se è necessario un valore di un determinato tipo, eseguire il cast di un valore letterale a tale tipo. Usare l'operatoreunchecked
se non è possibile rappresentare un valore letterale nel tipo di destinazione. Esempio:unchecked((int)0xFF_FF_FF_FF)
genera-1
.Se il valore letterale è suffisso da
U
ou
, il relativo tipo è il primo dei tipi seguenti in cui è possibile rappresentare il relativo valore:uint
,ulong
.Se il valore letterale è suffisso da
L
ol
, il relativo tipo è il primo dei tipi seguenti in cui è possibile rappresentare il relativo valore:long
,ulong
.Nota
È possibile usare la lettera minuscola
l
come suffisso. Tuttavia, questo genera un avviso del compilatore perché la letteral
può essere confusa con la cifra1
. UsareL
per maggiore chiarezza.Se il valore letterale è suffisso da
UL
,Ul
,uL
ul
,LU
,Lu
,lU
, olu
, il relativo tipo èulong
.
Se il valore rappresentato da un valore letterale Integer supera UInt64.MaxValue, si verifica un errore di compilazione CS1021.
Se il tipo determinato di un valore letterale intero è int
e il valore rappresentato dal valore letterale è compreso nell'intervallo del tipo di destinazione, il valore può essere convertito in modo implicito in sbyte
, byte
, short
, ushort
, uint
, ulong
, nint
o nuint
:
byte a = 17;
byte b = 300; // CS0031: Constant value '300' cannot be converted to a 'byte'
Come illustrato nell'esempio precedente, se il valore del valore letterale non rientra nell'intervallo del tipo di destinazione, si verifica un errore del compilatore CS0031.
È anche possibile usare un cast per convertire il valore rappresentato da un valore letterale interp nel tipo diverso dal tipo determinato del valore letterale:
var signedByte = (sbyte)42;
var longVariable = (long)42;
Conversioni
È possibile convertire qualsiasi tipo numerico integrale in qualsiasi altro tipo numerico integrale. Se il tipo di destinazione può archiviare tutti i valori del tipo di origine, la conversione è implicita. In caso contrario, è necessario usare un'espressione cast per eseguire una conversione esplicita. Per altre informazioni, vedere Conversioni numeriche predefinite.
Interi di dimensioni native
I tipi interi di dimensioni native hanno un comportamento speciale perché lo spazio di archiviazione è determinato dalle dimensioni intere naturali nel computer di destinazione.
Per ottenere le dimensioni di un intero di dimensioni native in fase di esecuzione, è possibile usare
sizeof()
. Tuttavia, il codice deve essere compilato in un contesto non sicuro. Ad esempio:Console.WriteLine($"size of nint = {sizeof(nint)}"); Console.WriteLine($"size of nuint = {sizeof(nuint)}"); // output when run in a 64-bit process //size of nint = 8 //size of nuint = 8 // output when run in a 32-bit process //size of nint = 4 //size of nuint = 4
È anche possibile ottenere il valore equivalente dalle proprietà statiche IntPtr.Size e UIntPtr.Size.
Per ottenere i valori minimo e massimo dei numeri interi di dimensioni native in fase di esecuzione, usare
MinValue
eMaxValue
come proprietà statiche con le parole chiavenint
enuint
, come nell'esempio seguente:Console.WriteLine($"nint.MinValue = {nint.MinValue}"); Console.WriteLine($"nint.MaxValue = {nint.MaxValue}"); Console.WriteLine($"nuint.MinValue = {nuint.MinValue}"); Console.WriteLine($"nuint.MaxValue = {nuint.MaxValue}"); // output when run in a 64-bit process //nint.MinValue = -9223372036854775808 //nint.MaxValue = 9223372036854775807 //nuint.MinValue = 0 //nuint.MaxValue = 18446744073709551615 // output when run in a 32-bit process //nint.MinValue = -2147483648 //nint.MaxValue = 2147483647 //nuint.MinValue = 0 //nuint.MaxValue = 4294967295
È possibile usare i valori costanti negli intervalli seguenti:
- Per
nint
: Int32.MinValue a Int32.MaxValue. - Per
nuint
: UInt32.MinValue a UInt32.MaxValue.
- Per
Il compilatore fornisce conversioni implicite ed esplicite in altri tipi numerici. Per altre informazioni, vedere Conversioni numeriche predefinite.
Non esiste una sintassi diretta per i valori letterali interi di dimensioni native. Non esiste alcun suffisso per indicare che un valore letterale è un intero di dimensioni native, ad esempio
L
per indicare un oggettolong
. È invece possibile usare cast impliciti o espliciti di altri valori interi. Ad esempio:nint a = 42 nint a = (nint)42;
Specifiche del linguaggio C#
Per altre informazioni, vedere le sezioni seguenti delle specifiche del linguaggio C#:
- Tipi integrali
- Valori letterali Integer
- Tipi integrali di dimensioni native
- C# 11 -
IntPtr
eUIntPtr
numerici