Notitie
Voor toegang tot deze pagina is autorisatie vereist. U kunt proberen u aan te melden of de directory te wijzigen.
Voor toegang tot deze pagina is autorisatie vereist. U kunt proberen de mappen te wijzigen.
Notitie
Dit artikel is een functiespecificatie. De specificatie fungeert als het ontwerpdocument voor de functie. Het bevat voorgestelde specificatiewijzigingen, samen met informatie die nodig is tijdens het ontwerp en de ontwikkeling van de functie. Deze artikelen worden gepubliceerd totdat de voorgestelde specificaties zijn voltooid en opgenomen in de huidige ECMA-specificatie.
Er kunnen enkele verschillen zijn tussen de functiespecificatie en de voltooide implementatie. Deze verschillen worden vastgelegd in de relevante LDM-notities (Language Design Meeting).
Meer informatie over het proces voor het aannemen van functiespeclets in de C#-taalstandaard vindt u in het artikel over de specificaties.
Probleem met de kampioen: https://github.com/dotnet/csharplang/issues/6065
Samenvatting
Dit is een revisie van de oorspronkelijke native integers feature (specificatie), waarbij de nint/nuint typen verschilden van de onderliggende typen System.IntPtr/System.UIntPtr.
Kortom, we behandelen nu nint/nuint als eenvoudige typen aliasing System.IntPtr/System.UIntPtr, zoals we doen voor int in relatie tot System.Int32. Met de System.Runtime.CompilerServices.RuntimeFeature.NumericIntPtr runtime-functievlag wordt dit nieuwe gedrag geactiveerd.
Ontwerpen
8.3.5 Eenvoudige typen
C# biedt een set vooraf gedefinieerde struct typen die de eenvoudige typen worden genoemd. De eenvoudige typen worden geïdentificeerd via trefwoorden, maar deze trefwoorden zijn gewoon aliassen voor vooraf gedefinieerde struct typen in de System naamruimte, zoals beschreven in de onderstaande tabel.
| trefwoord | gedefinieerd type |
|---|---|
sbyte |
System.SByte |
byte |
System.Byte |
short |
System.Int16 |
ushort |
System.UInt16 |
int |
System.Int32 |
uint |
System.UInt32 |
nint |
System.IntPtr |
nuint |
System.UIntPtr |
long |
System.Int64 |
ulong |
System.UInt64 |
char |
System.Char |
float |
System.Single |
double |
System.Double |
bool |
System.Boolean |
decimal |
System.Decimal |
[...]
8.3.6 Integrale typen
C# ondersteunt elf integrale typen: sbyte, byte, short, ushort, int, uint, nint, nuint, long, ulongen char. [...]
8.8 Niet-beheerde typen
Met andere woorden, een unmanaged_type is een van de volgende:
-
sbyte,byte,short,ushort,int,uint,nint,nuint,long,ulong,char,float,double,decimalofbool. - Elke enum_type.
- Door de gebruiker gedefinieerde struct_type die geen samengesteld type is en uitsluitend velden van unmanaged_typebevat.
- In onveilige code, elke pointertype.
10.2.3 Impliciete numerieke conversies
De impliciete numerieke conversies zijn:
- Van
sbytetotshort,int,nint,long,float,doubleofdecimal. - Van
bytetotshort,ushort,int,uint,nint,nuint,long,ulong,float,doubleofdecimal. - Van
shorttotint,nint,long,float,double, ofdecimal. - Van
ushorttotint,uint,nint,nuint,long,ulong,float,doubleofdecimal. - Van
inttotnint,long,float,doubleofdecimal. - Van
uinttotnuint,long,ulong,float,double, ofdecimal. -
van
ninttotlong,float,doubleofdecimal. -
van
nuinttotulong,float,doubleofdecimal. - Van
longtotfloat,double, ofdecimal. - Van
ulongtotfloat,double, ofdecimal. - Van
chartotushort,int,uint,nint,nuint,long,ulong,float,doubleofdecimal. - Van
floattotdouble.
[...]
10.2.11 Impliciete constante expressieconversies
Een impliciete conversie van constante expressies maakt de volgende conversies mogelijk:
- Een constant_expression van het type
intkan worden geconverteerd naar het typesbyte,byte,short,ushort,uint,nint,nuintofulong, mits de waarde van de constant_expression binnen het bereik van het doeltype valt. [...]
10.3.2 Expliciete numerieke conversies
De expliciete numerieke conversies zijn de conversies van een numeric_type naar een andere numeric_type waarvoor nog geen impliciete numerieke conversie bestaat:
- Van
sbytetotbyte,ushort,uint,nuint,ulong, ofchar. - Van
bytetotsbyteofchar. - Van
shorttotsbyte,byte,ushort,uint,nuint,ulongofchar. - Van
ushorttotsbyte,byte,shortofchar. - Van
intnaarsbyte,byte,short,ushort,uint,nuint,ulongofchar. - Van
uinttotsbyte,byte,short,ushort,int,nintofchar. - Van
longtotsbyte,byte,short,ushort,int,uint, ,nint,nuint,,ulongofchar. -
van
ninttotsbyte,byte,short,ushort,int,uint,nuint,ulongofchar. -
van
nuinttotsbyte,byte,short,ushort,int,uint,nint,longofchar. - Van
ulongtotsbyte,byte,short,ushort,int,uint, ,nint,nuint,,longofchar. - Van
chartotsbyte,byte, ofshort. - Van
floattotsbyte,byte,short,ushort,int,uint,nint,nuint,long,ulong,charofdecimal. - Van
doubletotsbyte,byte,short,ushort,int,uint, ,nint,nuint,,long,ulong,char,floatofdecimal. - Van
decimaltotsbyte,byte,short,ushort,int,uint, ,nint,nuint,,long,ulong,char,floatofdouble.
[...]
10.3.3 Expliciete opsommingsomzettingen
De expliciete opsommingsconversies zijn:
- Van
sbyte,byte,short,ushort,int,uint,nint,nuint,long,ulong,char,float,double, ofdecimalop een enum_type. - Van enum_type tot
sbyte,byte,short,ushort,int,uint,nint,nuint,long,ulong,char,float,doubleofdecimal. - Van elke enum_type naar elke andere enum_type.
12.6.4.7 Beter conversiedoel
Als we de twee typen T₁ en T₂beschouwen, is T₁ een betere conversiedoel dan T₂ als een van de volgende voorwaarden geldt:
- Er bestaat een impliciete conversie van
T₁naarT₂en er bestaat geen impliciete conversie vanT₂naarT₁ -
T₁isTask<S₁>,T₂isTask<S₂>enS₁is een beter conversiedoel danS₂ -
T₁isS₁ofS₁?waarbijS₁een ondertekend integraal type is enT₂isS₂ofS₂?waarbijS₂een niet-ondertekend integraaltype is. Specifiek: [...]
12.8.12 Elementtoegang
[...] Het aantal expressies in de argument_list moet gelijk zijn aan de rang van de array_typeen elke expressie moet van het type int, uint, nint, nuint, longof ulong, zijn of impliciet kunnen worden omgezet in een of meer van deze typen.
11.8.12.2 Matrixtoegang
[...] Het aantal expressies in de argument_list moet gelijk zijn aan de rang van de array_typeen elke expressie moet van het type int, uint, nint, nuint, longof ulong, zijn of impliciet kunnen worden omgezet in een of meer van deze typen.
[...] De tijdsverwerking van een arraytoegang van het formulier P[A], waarbij P een primary_no_array_creation_expression is van een arraytype en A een argument_listis, bestaat uit de volgende stappen: [...]
- De indexexpressies van de argument_list worden op volgorde geëvalueerd, van links naar rechts. Na de evaluatie van elke indexexpressie wordt een impliciete conversie naar een van de volgende typen uitgevoerd:
int,uint,nint,nuint,long,ulong. Het eerste type in deze lijst waarvoor een impliciete conversie bestaat, wordt gekozen. [...]
12.8.16 Postfix incrementeer- en decrementeeroperatoren
De overbelastingsresolutie van unaire operatoren wordt gebruikt om een specifieke operatorimplementatie te selecteren. Vooraf gedefinieerde operatoren voor ++ en -- bestaan voor de volgende typen: sbyte, byte, short, ushort, int, uint, nint, nuint,long, ulong, char, float, double, decimalen elk enumtype.
12.9.2 Unary plus operator
De vooraf gedefinieerde unaire plusoperators zijn:
...
nint operator +(nint x);
nuint operator +(nuint x);
12.9.3 Unaire mintekenoperator
De vooraf gedefinieerd unaire minus-operatoren zijn:
Negatie van gehele getallen:
... nint operator –(nint x);
12.8.16 Postfix incrementeer- en decrementeeroperatoren
Vooraf gedefinieerde ++- en -- operators bestaan voor de volgende typen: sbyte, byte, short, ushort, int, uint, nint, nuint, long, ulong, char, float, double, decimalen een opsommingstype.
11.7.19 Standaardwaardeexpressies
Bovendien is een default_value_expression een constante expressie als het type een van de volgende waardetypen is: sbyte, byte, short, ushort, int, uint, nint, nuint, long, ulong, char, float, double, decimal, bool, of een opsommingstype.
12.9.5 Bitsgewijze complementoperator
De vooraf gedefinieerde bitsgewijze complementoperators zijn:
...
nint operator ~(nint x);
nuint operator ~(nuint x);
12.9.6 Prefix-verhogings- en verlagingsoperatoren
Vooraf gedefinieerde ++- en -- operators bestaan voor de volgende typen: sbyte, byte, short, ushort, int, uint, nint, nuint, long, ulong, char, float, double, decimalen een opsommingstype.
12.10 Rekenkundige operatoren
12.10.2 Vermenigvuldigingsoperator
De vooraf gedefinieerde vermenigvuldigingsoperatoren worden hieronder vermeld. De operators berekenen allemaal het product van x en y.
Vermenigvuldiging van gehele getallen:
... nint operator *(nint x, nint y); nuint operator *(nuint x, nuint y);
12.10.3 Divisieoperator
Hieronder vindt u de vooraf gedefinieerde divisieoperators. De operators berekenen allemaal het quotiënt van x en y.
Deling van gehele getallen:
... nint operator /(nint x, nint y); nuint operator /(nuint x, nuint y);
Operator 12.10.4 Rest
De vooraf gedefinieerde restoperators worden hieronder weergegeven. De operators berekenen allemaal de rest van de deling tussen x en y.
Restgetal geheel getal:
... nint operator %(nint x, nint y); nuint operator %(nuint x, nuint y);
12.10.5 Optellen operator
Optellen van gehele getallen:
... nint operator +(nint x, nint y); nuint operator +(nuint x, nuint y);
12.10.6 Aftrekkingsoperator
Geheel getal aftrekken:
... nint operator –(nint x, nint y); nuint operator –(nuint x, nuint y);
12.11 Shift-operatoren
De vooraf gedefinieerde shiftoperators worden hieronder weergegeven.
Naar links verschuiven:
... nint operator <<(nint x, int count); nuint operator <<(nuint x, int count);Naar rechts gaan:
... nint operator >>(nint x, int count); nuint operator >>(nuint x, int count);De operator
>>verschuiftxnaar rechts door een aantal bits dat is berekend, zoals hieronder wordt beschreven.Wanneer
xvan het typeint,nintoflongis, worden de laagwaardige bits vanxverwijderd, worden de resterende bits naar rechts verschoven, en worden de hoogwaardige lege bitposities ingesteld op nul alsxniet-negatief is en op één alsxnegatief is.Wanneer
xvan het typeuint,nuintofulongis, worden de lage volgorde vanxverwijderd, worden de resterende bits naar rechts verplaatst en worden de lege bitposities in hoge volgorde ingesteld op nul.Niet-ondertekende dienst rechts:
... nint operator >>>(nint x, int count); nuint operator >>>(nuint x, int count);
Voor de vooraf gedefinieerde operators wordt het aantal bits dat moet worden verplaatst als volgt berekend: [...]
- Wanneer het type
xnintofnuintis, wordt het aantal verschuivingen gegeven door de laagste vijf bits vancountop een 32-bits platform of de zes laagste bits vancountop een 64-bits platform.
12.12 Relationele en typetestoperators
12.12.2 Vergelijkingsoperatoren voor gehele getallen
De vooraf gedefinieerde vergelijkingsoperatoren voor gehele getallen zijn:
...
bool operator ==(nint x, nint y);
bool operator ==(nuint x, nuint y);
bool operator !=(nint x, nint y);
bool operator !=(nuint x, nuint y);
bool operator <(nint x, nint y);
bool operator <(nuint x, nuint y);
bool operator >(nint x, nint y);
bool operator >(nuint x, nuint y);
bool operator <=(nint x, nint y);
bool operator <=(nuint x, nuint y);
bool operator >=(nint x, nint y);
bool operator >=(nuint x, nuint y);
12.12 Logische operators
12.12.2 Logische operatoren voor gehele getallen
De vooraf gedefinieerde logische operatoren voor gehele getallen zijn:
...
nint operator &(nint x, nint y);
nuint operator &(nuint x, nuint y);
nint operator |(nint x, nint y);
nuint operator |(nuint x, nuint y);
nint operator ^(nint x, nint y);
nuint operator ^(nuint x, nuint y);
12.22 Constante uitdrukkingen
Een constante expressie kan een waardetype of een verwijzingstype zijn. Als een constante expressie een waardetype is, moet dit een van de volgende typen zijn: sbyte, byte, short, ushort, int, uint, nint, nuint, long, ulong, char, float, double, decimal, bool, of een opsommingstype.
[...]
Bij een impliciete expressieconversie kan een constante expressie van het type int worden geconverteerd naar sbyte, byte, short, ushort, uint, nint, nuint, of ulong, mits de waarde van de constante expressie binnen het bereik van het doeltype valt.
17.4 Toegang tot matrixelementen
Matrixelementen worden geopend met behulp van element_access expressies van het formulier A[I₁, I₂, ..., Iₓ], waarbij A een expressie van een matrixtype is en elke Iₑ een expressie is van het type int, uint, nint, nuint,long, ulongof impliciet kan worden geconverteerd naar een of meer van deze typen. Het resultaat van toegang tot een matrixelement is een variabele, namelijk het matrixelement dat door de indexen is geselecteerd.
23.5 Aanwijzerconversies
23.5.1 Algemeen
[...]
Bovendien wordt in een onveilige context de set beschikbare expliciete conversies uitgebreid met de volgende expliciete aanwijzerconversies:
- Van elke pointer_type naar elke andere pointer_type.
- Van
sbyte,byte,short,ushort,int,uint,nint,nuint,longofulongop een pointer_type. - Van pointer_type tot
sbyte,byte,short,ushort,int,uint,nint,nuint,long, totulong.
23.6.4 Toegang tot aanwijzerelementen
[...] In een verwijzingselementtoegang van het formulier P[E]moet P een expressie zijn van een ander type aanwijzer dan void*en moet E een expressie zijn die impliciet kan worden geconverteerd naar int, uint, nint, nuint,longof ulong.
23.6.7 Pointer-aritmetica
In een onveilige context kunnen de operator + en – worden toegepast op waarden van alle typen aanwijzers, met uitzondering van void*. Voor elk type aanwijzer T*worden de volgende operators dus impliciet gedefinieerd:
[...]
T* operator +(T* x, nint y);
T* operator +(T* x, nuint y);
T* operator +(nint x, T* y);
T* operator +(nuint x, T* y);
T* operator -(T* x, nint y);
T* operator -(T* x, nuint y);
Gezien een expressie P van een aanwijzertype T* en een expressie N van het type int, uint, nint, nuint,longof ulong, berekenen de expressies P + N en N + P de aanwijzerwaarde van het type T* die voortkomt uit het optellen van N * sizeof(T) bij het adres opgegeven door P. Op dezelfde manier berekent de expressie P – N de aanwijzerwaarde van het type T* die het gevolg is van het aftrekken van N * sizeof(T) van het adres dat is opgegeven door P.
Verschillende overwegingen
Belangrijke wijzigingen
Een van de belangrijkste gevolgen van dit ontwerp is dat System.IntPtr en System.UIntPtr enkele ingebouwde operators (conversies, unaire en binaire) krijgen.
Deze omvatten checked operators, wat betekent dat de volgende operators op deze typen nu worden gegenereerd wanneer deze overlopen:
IntPtr + intIntPtr - intIntPtr -> intlong -> IntPtrvoid* -> IntPtr
Metagegevenscodering
Dit ontwerp betekent dat nint en nuint eenvoudig kunnen worden verzonden als System.IntPtr en System.UIntPtr, zonder gebruik te maken van System.Runtime.CompilerServices.NativeIntegerAttribute.
Op dezelfde manier kan NativeIntegerAttribute worden genegeerd bij het laden van metagegevens.
C# feature specifications