Middle
Wie funktioniert shared_ptr in C++?
sobes.tech KI
Antwort von AI
shared_ptr — ist ein intelligenter Zeiger, der die Besitzsemantik einer geteilten Ressource implementiert. Er speichert einen Zeiger auf das Objekt und einen Zeiger auf den Steuerblock.
Der Steuerblock enthält:
- Zähler für starke Referenzen (reference count).
- Zähler für schwache Referenzen (weak count).
- Benutzerdefinierter Löschfunktor (deleter), falls angegeben.
- Benutzerdefinierter Allokator, falls angegeben.
- Zeiger auf das gespeicherte Objekt (das gleiche wie im
shared_ptr).
Funktionsweise:
- Erstellung: Beim Erstellen des ersten
shared_ptr, der auf ein Objekt zeigt, wird der Steuerblock erstellt, und die Referenzzähler werden initialisiert: stark — 1, schwach — 0.std::shared_ptr<int> ptr1 = std::make_shared<int>(10); // Erstellt ein int-Objekt und einen Steuerblock - Kopie: Beim Kopieren eines
shared_ptrerhöht sich der Zähler für starke Referenzen im Steuerblock um 1.std::shared_ptr<int> ptr2 = ptr1; // Erhöht den Zähler für starke Referenzen - Zuweisung: Beim Zuweisen eines
shared_ptrwird die alte Ressource dekrementiert (starker Referenzzähler sinkt), und die neue Ressource wird inkrementiert (steigt).std::shared_ptr<int> ptr3; ptr3 = ptr1; // Dekrementiert die alte Ressource von ptr3, Inkrementiert die Ressource von ptr1 - Löschung: Beim Zerstören eines
shared_ptr(z.B. Verlassen des Gültigkeitsbereichs) wird der Zähler für starke Referenzen dekrementiert.{ std::shared_ptr<int> ptr4 = ptr1; // Erhöht den Zähler für starke Referenzen // ptr4 verlässt den Gültigkeitsbereich } // Dekrementiert den Zähler für starke Referenzen - Freigabe der Ressource: Wenn der Zähler für starke Referenzen null erreicht, wird die Ressource (das Objekt, auf das
shared_ptrzeigt) mit dem definierten Löschfunktor (oderdeletestandardmäßig) gelöscht. - Freigabe des Steuerblocks: Der Steuerblock wird freigegeben, wenn beide Zähler (stark und schwach) null erreichen.
Vorteile:
- Automatische Speicherverwaltung für geteilte Ressourcen.
- Sicherheit vor doppeltem Freigeben.
- Unterstützung benutzerdefinierter Löschfunktoren.
Nachteile:
- Zyklische Referenzen können zu Speicherlecks führen (gelöst mit
weak_ptr). - Geringfügiger Mehraufwand durch Steuerblock und atomare Operationen an den Zählern.
- Sicherheit bei Operationen mit dem eigenen
shared_ptr(Kopieren, Zuweisung, Änderung des gespeicherten Zeigers), aber nicht mit dem Objekt, auf das er zeigt.