Típuskonverziók, típusátalakítás és csomagolás

Tip

Új szoftverfejlesztés? Először az Első lépések oktatóanyagokkal kezdje. Az alapszintű típusokat ott gyakorolhatja, mielőtt konverziós döntéseket hoz.

Tapasztalt egy másik nyelven? A C#-konverziók a legtöbb statikusan típusos nyelvhez hasonlóan működnek: a szélesítő konverziók implicit, a szűkítő konverziókhoz explicit kasztolásra van szükség, a szöveget elemezve előnyben kell részesíteni a TryParse-t a felhasználói felületű kódban.

C#-kód írásakor gyakran konvertálja az értékeket egyik típusból a másikba. Konvertálhat például int-ról long-re, beolvashat és számmá konvertálhat egy szöveget, vagy egy alaptípust származtatott típussá alakíthat.

A legfontosabb kifejezések ismertetése:

  • Az átalakítás az érték egyik típusról a másikra történő módosításának folyamata.
  • A cast az olyan explicit típuskonverzió szintaxisa, amelyet zárójelek közé írunk, mint például (int)value.
  • Az implicit átalakítás olyan átalakítás, amely automatikusan megtörténik, amikor a fordító képes garantálni a biztonságos műveletet.
  • Az explicit típuskonverzió egy kódba írt átalakítás, amely jelzi, hogy az átalakítás során információ elveszhet, vagy sikertelen lehet.

Egyezzen a konvertálási stílussal a helyzethez:

  • Az implicit konverziók automatikusan történnek, ha a fordító képes garantálni a biztonságot – nincs szükség szintaxisra.
  • Explicit leadásokra van szükség, ha az adatok elveszhetnek, vagy az átalakítás sikertelen lehet.
  • A mintaegyeztetés as akkor alkalmazható, ha olyan biztonságos referenciatípus-átalakításra van szüksége, amely esetleg nem sikerül.
  • Az API-k elemzése akkor érvényes, ha a forrásérték szöveg.

Implicit és explicit numerikus konverziók

Az implicit átalakítás mindig sikeres. Előfordulhat, hogy egy explicit átalakítás sikertelen vagy adatvesztést eredményez.

int itemCount = 42;
long widened = itemCount; // Implicit conversion.

double average = 19.75;
int truncated = (int)average; // Explicit cast.

Console.WriteLine($"widened: {widened}, truncated: {truncated}");

Egy explicit stáb tájékoztatja az olvasókat, hogy az átalakítás adatai elveszhetnek. A mintában az double érték levágásra kerül, amikor int-ré alakul.

A teljes konverziós táblákért lásd a beépített numerikus átalakításokat.

Hivatkozások konvertálása

Az osztályok referenciatípusok. Az típuskonverziók nem másolnak adatokat. Megváltoztatják, hogyan tekintheti meg ugyanazt az objektumot.

Egyes referenciakonverziók implicitek. A fordító garantálja, hogy biztonságosak. Három helyzet mindig implicit referenciakonverziót eredményez: származtatott osztálypéldány hozzárendelése alaposztályváltozóhoz (a származtatott típus az alaptípus altípusa), referenciatípus-példány hozzárendelése egy olyan interfész változóhoz, amelyet a típus implementál, és bármilyen referenciatípus hozzárendelése egy object változóhoz.

Mammal otter = new() { Name = "River otter" };
Animal animal = otter;           // Derived to base class: always safe.
INamed named = otter;            // Reference type to implemented interface: always safe.
object obj = otter;              // Any reference type to object: always safe.

Console.WriteLine(named.Name);

Az alaptípustól a származtatott típusig eltérő irányban történő visszalépéshez explicit ellenőrzés szükséges, mivel előfordulhat, hogy az objektum valójában nem a várt származtatott típus. A mintaegyezést részesítse előnyben, hogy a tesztelés és a hozzárendelés együtt történjen.

Animal knownAnimal = new Mammal { Name = "River otter" };

if (knownAnimal is Mammal mammal)
{
    Console.WriteLine($"Pattern match succeeded: {mammal.Name}");
}

Animal unknownAnimal = new Reptile();
Console.WriteLine($"Can treat as mammal: {unknownAnimal is Mammal}");

A mintaegyezés megtartja a sikeres öntött változót a legkisebb gyakorlati hatókörben, ami javítja az olvashatóságot.

Ha feltételes ág helyett null értékű eredményre van szüksége, használja a következőt as:

object boxedMammal = new Mammal { Name = "Sea lion" };
Mammal? maybeMammal = boxedMammal as Mammal;
Console.WriteLine(maybeMammal is null ? "Not a mammal" : maybeMammal.Name);

object boxedReptile = new Reptile();
Mammal? noMammal = boxedReptile as Mammal;
Console.WriteLine(noMammal is null ? "Safe null result" : noMammal.Name);

Csak hivatkozástípusokkal és nullértékű értéktípusokkal használható as . Akkor ad null vissza, ha az átalakítás sikertelen.

A csomagolás és kicsomagolás megértése

A Boxing egy struktúra - vagy egyéb értéktípust implementált felülettípussá object vagy -típussá alakít át. A kicsomagolás kinyeri az értéktípust az objektumhivatkozásból.

int temperature = 72;
object boxedTemperature = temperature; // Boxing.
int unboxedTemperature = (int)boxedTemperature; // Unboxing.

Packet packet = new(7);
ILabelled labelledPacket = packet; // Boxing through an interface reference.

Console.WriteLine($"Unboxed: {unboxedTemperature}, Label: {labelledPacket.Label}");

A boxing lefoglalja a memóriát a felügyelt halomon, és a kicsomagoláshoz típusellenőrzésre van szükség. A gyakori elérésű útvonalakon kerülje a felesleges boxolást, mert kiosztásokat és extra munkát ad hozzá.

Szöveg elemzése a Parse és a TryParse használatával

A felhasználói bemenetek vagy fájltartalmak konvertálásakor kezdje az alábbival TryParse: . Elkerüli a várt érvénytelen bemenetek kivételeit, és explicité teszi a hibakezelést. Minden elemzési API létrehoz egy új objektum- vagy értéktípus-példányt a forrássztringből; nem módosítják a forrást.

string textValue = "512";
int parsed = int.Parse(textValue);

string userInput = "12x";
bool parsedSuccessfully = int.TryParse(userInput, out int safeValue);

Console.WriteLine($"parsed: {parsed}");
Console.WriteLine(parsedSuccessfully ? $"safe value: {safeValue}" : "Input is not a valid number.");

Akkor használható Parse , ha a bemenet érvényes, például ellenőrzött tesztadatok. Felhasználói bevitelhez, hálózati hasznos adatokhoz és fájladatokhoz használható TryParse .

Alapvető konverziós API-k

Ezeket az API-kat leggyakrabban a mindennapi kódban használhatja:

A speciális konverziós viselkedés és az összes túlterhelés esetén tekintse át az adott céltípus API-referenciáját.

Lásd még