C++-də unique_ptr istifadə edərkən yaddaş sızması necə baş verə bilər?
AI-dan cavab
sobes.tech Süni İntellekt
std::unique_ptr istifadə edərkən yaddaş sızması aşağıdakı hallarda baş verə bilər:
-
Öz deleterinizin düzgün istifadə edilməməsi: Əgər xüsusi deleter düzgün sərbəst buraxmırsa (məsələn,
deleteyerinədelete[]array üçün və ya müvafiq sərbəst buraxma funksiyasını çağırmırsa).#include <memory> #include <iostream> struct MyDeleter { void operator()(int* ptr) const { // SƏHVI: delete[] olmalı idi, delete yox delete ptr; std::cout << "Yanlış deleter çağırıldı" << std::endl; } }; int main() { // Array ayırma, amma yanlış deleter istifadə olunur std::unique_ptr<int, MyDeleter> ptr(new int[10], MyDeleter()); // Ayırılan array tamamilə sərbəst buraxılmayacaq return 0; } -
unique_ptr-dən alınan xam göstəricinin başqa funksiyaya ötürülməsi və onun mülkiyyətinin alınması və sərbəst buraxılmaması: Mülkiyyət açıq şəkildəstd::moveilə ötürülməlidir. Əgərget()və ya xam göstərici ötürülür və sonra sərbəst buraxılmırsa, yaddaş sızması baş verə bilər.#include <memory> #include <iostream> void process_and_lose(int* raw_ptr) { // raw_ptr delete edilmir std::cout << "İşlənən " << *raw_ptr << std::endl; // Yaddaş sızması! } int main() { std::unique_ptr<int> ptr(new int(42)); int* raw = ptr.get(); process_and_lose(raw); // ptr hələ də yaddaşı idarə edir, amma raw göstərici artıq mülkiyyətdən çıxıb // Bu nümunədə sızma yoxdur, çünki ptr sərbəst buraxır // Amma əgər ptr əvvəlcə sıfırlanıb və ya başqa yerə yönəldilərsə, sızma baş verərdi return 0; }Düzgünləşdirilmiş nümunə, potensial sızma ilə (mülkiyyət ötürülür, amma funksiya sərbəst buraxmır):
#include <memory> #include <iostream> void function_that_takes_ownership_and_leaks(int* owned_ptr) { // Bu funksiya owned_ptr-in artıq onun mülkiyyətində olduğunu qəbul edir std::cout << "Mülkiyyət alındı və sızdırıldı: " << *owned_ptr << std::endl; // Sızma: owned_ptr sərbəst buraxılmır } int main() { std::unique_ptr<int> ptr(new int(100)); // Xam göstəricinin mülkiyyətini ötürürük function_that_takes_ownership_and_leaks(ptr.release()); // ptr indi boşdur, onun resursu (göstərici) avtomatik sərbəst buraxılmayacaq return 0; } -
Yaddaş ayırmadan və
unique_ptr-ə bağlamadan əvvəlki istisnalar:std::make_uniquebunu qarşısını alır, amma birbaşanewistifadə və sonraunique_ptr-ə bağlama, əgər aralarına istisna düşərsə, sızmaya səbəb ola bilər.#include <memory> #include <vector> class Resource { public: Resource() { std::cout << "Resurs yaradıldı" << std::endl;} ~Resource() { std::cout << "Resurs məhv edildi" << std::endl;} }; void might_throw() { throw std::runtime_error("Oops!"); } int main() { Resource* res = new Resource(); // Yaddaş ayırma try { might_throw(); // İstisna burada baş verir std::unique_ptr<Resource> ptr(res); // Bu sətir icra olunmayacaq } catch (const std::runtime_error& e) { std::cerr << "İstisna tutuldu: " << e.what() << std::endl; // res* sərbəst buraxılmayıb və `unique_ptr`-ə bağlanmayıb // Bu, sızmaya səbəb olur! } // Doğru üsul: std::make_unique<Resource>() və ya std::unique_ptr<Resource> ptr(new Resource()); return 0; }
Ümumiyyətlə, std::unique_ptr-in düzgün istifadəsində yaddaş sızması çox az ehtimal olunur, çünki onun əsas məqsədi resursların avtomatik idarə olunmasıdır və tipik ssenarilərdə sızmaları qarşısını alır. Problemlər onun standart istifadəsindən kənara çıxıldıqda yaranır (öz deleterlər, release(), xam göstəricilərlə qarşılıqlı əlaqə).