Generische Strukturen in C# (List<T>, Dictionary<TKey,TValue>)
Lernen Sie Generics in C# (List<T>, Dictionary<TKey,TValue>), um typsicheren, wiederverwendbaren Code zu schreiben.
In C# werden Generics verwendet, um die Typsicherheit und Flexibilität zu erhöhen. Generische Klassen und Collections vermeiden Laufzeit-Typumwandlungen sowie unnötige Boxing- und Unboxing-Vorgänge, wodurch die Performance verbessert und das Fehlerrisiko reduziert wird.
Bevor Generics eingeführt wurden, speicherten Collections wie ArrayList ihre Elemente als object. Wenn ein Werttyp wie int zu einer ArrayList hinzugefügt wurde, musste er „geboxt“ (in object konvertiert) und beim Auslesen wieder „entboxt“ werden. Dieser Boxing-/Unboxing-Prozess verursachte zusätzliche Speicherzuweisungen und Performance-Overhead.
Mit generischen Collections wie List<T> und Dictionary<TKey,TValue> werden Elemente in ihrem tatsächlichen Typ gespeichert. Dadurch entfallen diese Kosten und der Code wird sowohl sicherer als auch schneller.
List<T>
List<T> ist eine generische Kollektion, die Elemente eines bestimmten Typs dynamisch speichert.
T gibt den Typ der Elemente an, die die Liste enthalten soll.
using System;
using System.Collections.Generic;
var zahlen = new List<int>();
zahlen.Add(10);
zahlen.Add(20);
zahlen.Add(30);
foreach (int z in zahlen)
Console.WriteLine(z);
// Ausgabe:
// 10
// 20
// 30
Hinweis: Im Gegensatz zu Arrays kann List<T> dynamisch wachsen und schrumpfen.
Dictionary<TKey,TValue>
Dictionary ist eine generische Schlüssel–Wert-Kollektion.
TKey gibt den Typ des Schlüssels an, TValue den Typ des Wertes.
using System;
using System.Collections.Generic;
var studenten = new Dictionary<int, string>();
studenten[101] = "Max";
studenten[102] = "Anna";
studenten[103] = "Lukas";
foreach (var kv in studenten)
Console.WriteLine($"{kv.Key} → {kv.Value}");
// Ausgabe:
// 101 → Max
// 102 → Anna
// 103 → Lukas
Hinweis: Jeder Key in einem Dictionary muss eindeutig sein.
Der Versuch, denselben Schlüssel erneut hinzuzufügen, führt zu einem Fehler.
Eigene generische Klassen erstellen
Sie können nicht nur vordefinierte Kollektionen verwenden, sondern auch eigene generische Typen definieren. Dadurch entstehen wiederverwendbare und typensichere Strukturen.
public class Box<T>
{
public T Wert { get; set; }
public void Drucken()
{
Console.WriteLine($"Box enthält: {Wert}");
}
}
class Program
{
static void Main()
{
var intBox = new Box<int> { Wert = 42 };
intBox.Drucken();
var stringBox = new Box<string> { Wert = "Hallo" };
stringBox.Drucken();
}
}
// Ausgabe:
// Box enthält: 42
// Box enthält: Hallo
Generische Einschränkungen (Constraints)
Generische Typen können Einschränkungen (mit dem Schlüsselwort where) verwenden,
um bestimmte Anforderungen an die Typparameter durchzusetzen.
public class Repository<T> where T : class
{
private readonly List<T> _items = new();
public void Hinzufügen(T item) => _items.Add(item);
public void DruckenAlle()
{
foreach (var i in _items)
Console.WriteLine(i);
}
}
class Program
{
static void Main()
{
var repo = new Repository<string>();
repo.Hinzufügen("Stift");
repo.Hinzufügen("Heft");
repo.DruckenAlle();
}
}
// Ausgabe:
// Stift
// Heft
Beispielanwendung: Produktverwaltung
Im folgenden Beispiel werden Produktinformationen in einer List<Product> gespeichert,
und Produkt-ID–Namen-Zuordnungen in einem Dictionary<int,string>.
public class Product
{
public int Id { get; set; }
public string Name { get; set; } = string.Empty;
}
class Program
{
static void Main()
{
var produkte = new List<Product>
{
new Product { Id = 1, Name = "Laptop" },
new Product { Id = 2, Name = "Telefon" }
};
var produktDict = new Dictionary<int, string>();
foreach (var p in produkte)
produktDict[p.Id] = p.Name;
Console.WriteLine("Produkte:");
foreach (var kv in produktDict)
Console.WriteLine($"{kv.Key} - {kv.Value}");
}
}
// Ausgabe:
// Produkte:
// 1 - Laptop
// 2 - Telefon
LINQ-Alternative: Sie können die Liste auch direkt mit ToDictionary in ein Dictionary umwandeln.
var produktDict = produkte.ToDictionary(p => p.Id, p => p.Name);
Console.WriteLine("Produkte:");
foreach (var kv in produktDict)
Console.WriteLine($"{kv.Key} - {kv.Value}");
Kurz & Knapp
- Generics verbessern die Typensicherheit und Wiederverwendbarkeit.
List<T>: Dynamische, typensichere Liste.Dictionary<TKey,TValue>: Schnelle Suche mit eindeutigen Schlüsseln.- Sie können eigene generische Klassen erstellen und mit Einschränkungen Typensicherheit erzwingen.
- Generics sind performant und reduzieren die Notwendigkeit von Boxing/Unboxing.
Ähnliche Artikel
Arrays (Felder) in C#
Lernen Sie Arrays in C#, inklusive Deklaration, Indexzugriff, Schleifen und typischer Array-Operationen mit Beispielen.
Kollektionen in C#: Liste, Wörterbuch, Warteschlange, Stapel
Lernen Sie Collections in C# wie List, Dictionary, Queue und Stack kennen, um Daten effizient zu verwalten – mit Beispielen.
Typumwandlungen in C#
Erlernen Sie Typumwandlungen in C#, einschließlich impliziter und expliziter Konvertierung sowie Parse-, TryParse- und Convert-Methoden.