Junior
Ποιοι έξυπνοι δείκτες υπάρχουν στη C++;
sobes.tech AI
Απάντηση από AI
std::unique_ptr, std::shared_ptr, std::weak_ptr.
-
std::unique_ptr:- Αποκλειστική ιδιοκτησία του αντικειμένου.
- Δεν μπορεί να αντιγραφεί, αλλά μπορεί να μετακινηθεί (
std::move). - Αυτόματα διαγράφει το αντικείμενο όταν βγει από το πεδίο ορατότητας ή καταστραφεί το
unique_ptr. - Είναι ελαφρύ, χωρίς πρόσθετα έξοδα για τον μετρητή αναφορών.
#include <memory> // Δημιουργία unique_ptr std::unique_ptr<int> up1(new int(10)); // Μεταφορά ιδιοκτησίας std::unique_ptr<int> up2 = std::move(up1); // up1 τώρα είναι nullptr // up2 κατέχει το αντικείμενο -
std::shared_ptr:- Κοινή ιδιοκτησία του αντικειμένου.
- Χρησιμοποιεί έναν μετρητή αναφορών για να παρακολουθεί πόσα
shared_ptrδείχνουν στην πηγή. - Το αντικείμενο διαγράφεται όταν ο τελευταίος
shared_ptrπου το δείχνει καταστρέφεται. - Μπορεί να αντιγραφεί και να μετακινηθεί.
- Έχει πρόσθετα έξοδα για τον μετρητή αναφορών (συνήθως διαχωριστά κατανεμημένο).
- Μπορεί να σχηματίσει κυκλικές αναφορές, που οδηγούν σε διαρροές μνήμης.
#include <memory> // Δημιουργία shared_ptr std::shared_ptr<int> sp1 = std::make_shared<int>(20); // Αντιγραφή ιδιοκτησίας std::shared_ptr<int> sp2 = sp1; // Ο μετρητής αναφορών αυξάνεται // sp1 και sp2 κατέχουν το αντικείμενο -
std::weak_ptr:- Δεν κατέχει το αντικείμενο.
- Αντιπροσωπεύει μια "αδύναμη" αναφορά στο αντικείμενο, που διαχειρίζεται από ένα ή περισσότερα
shared_ptr. - Χρησιμοποιείται για την αποτροπή κυκλικών αναφορών μεταξύ
shared_ptr. - Δεν αυξάνει τον μετρητή αναφορών του αντικειμένου.
- Για ασφαλή πρόσβαση στο αντικείμενο, πρέπει να μετατραπεί σε
shared_ptrμε τη μέθοδοlock(). Αν το αντικείμενο έχει ήδη διαγραφεί, τοlock()θα επιστρέψει ένα κενόshared_ptr.
#include <memory> // Δημιουργία shared_ptr std::shared_ptr<int> sp = std::make_shared<int>(30); // Δημιουργία weak_ptr από shared_ptr std::weak_ptr<int> wp = sp; // Έλεγχος και χρήση του αντικειμένου if (auto shared_from_weak = wp.lock()) { // Πρόσβαση στο αντικείμενο μέσω shared_from_weak } else { // Το αντικείμενο έχει ήδη διαγραφεί }