Modül dersleri (2/2)
std::zayıf_ptr
std::shared_ptr son derece yararlı olmasına rağmen, yalnızca ortak sahipliğe güvenmek döngüsel referans (veya döngüsel bağımlılık) olarak bilinen bir soruna yol açabilir.
İki veya daha fazla nesnenin her biri diğerine işaret eden bir shared_ptr içeriyorsa kapalı bir döngü oluşturulur. Bu durumda, hiçbir nesnenin referans sayısı hiçbir zaman sıfıra ulaşmaz, bu da dağıtımın kaldırılmasını önler ve bellek sızıntısına neden olur.
std::weak_ptr nedir?
Sahiplik döngülerini kırmak için standart kütüphane std::weak_ptr olanağını sunar. Bu, shared_ptr tarafından yönetilen bir nesneyi referans sayısını artırmadan gözlemleyen akıllı bir işaretçidir.
Kaynağın doğrudan sahibi olmadığı için yok edilmesini engellemez.
#include <memory>
std::shared_ptr<int> shared = std::make_shared<int>(42);
std::weak_ptr<int> weak = shared; // Does not increment reference count!Kaynağı Doğrulama ve Erişme
Bir weak_ptr kaynağın sahibi olmadığından, kaynağın tahsisi herhangi bir zamanda serbest bırakılabilir (ilişkili tüm shared_ptr örnekleri kapsam dışına çıktığında).
Gözlemlenen kaynağı kullanmak için şunları yapmalıyız:
expired()kullanarak hala geçerli olup olmadığını kontrol edin.lock()yöntemini kullanarakweak_ptröğesini geçici olarakshared_ptrbiçimine dönüştürün. Kaynak hala etkinse,lock()geçerli birshared_ptrdöndürür, aksi takdirde bir boş işaretçi (nullptr) döndürür.
if (!weak.expired()) {
// lock() creates a temporary shared_ptr to ensure safe access
if (std::shared_ptr<int> sharedAccess = weak.lock()) {
std::cout << *sharedAccess << std::endl;
}
} else {
std::cout << "Resource deallocated!" << std::endl;
}Kendin dene
sPtr'den başlatılan wPtr adında bir std::weak_ptr<int> bildirin. Daha sonra wPtr.expired() tarafından döndürülen boole sonucunu std::cout kullanarak yazdırın.
İpucu göster
Aynı genel türü "<int>" gösteren "weak_ptr"i bildirin ve ona doğrudan "sPtr"yi atayın.
3 denemeden sonra çözüm mevcut
Geçici bir paylaşılan_ptr elde etmek için wPtr'de lock() yöntemini kullanın. İşlem başarılı olursa (işaretçi boş değilse), başvurulan değeri yazdırın.
İpucu göster
'wPtr.lock()'u çağırarak bir 'if' bloğu içindeki bir değişkeni başlatın, ardından yıldız işareti '*' ile kaynağın referansını kaldırarak yazdırın.
3 denemeden sonra çözüm mevcut