Sınıf üyeleri için kullanarak akıllı işaretçiler
Sorun C 11 sınıf üyeleri olarak akıllı işaretlerini kullanma anlamakta güçlük çekiyorum. Akıllı işaretçiler hakkında çok şey okudum ve unique_ptr
veshared_ptr
/weak_ptr
genel olarak nasıl çalıştığını sanırım anlıyorum. Anlamadığım şey gerçek kullanımı. Herkes hemen hemen her zaman gitmek için yol olarak unique_ptr
kullanarak önerir gibi görünüyor. Ama nasıl böyle bir şey uygulamak istiyorum
class Device {
};
class Settings {
Device *device;
public:
Settings(Device *device) {
this->device = device;
}
Device *getDevice() {
return device;
}
};
int main() {
Device *device = new Device();
Settings settings(device);
// ...
Device *myDevice = settings.getDevice();
// do something with myDevice...
}
Hadi akıllı işaretçiler işaretçiler değiştirilmesini istiyorum deyin. unique_ptr
getDevice()
, çünkü işe yaramaz bir değil mi? shared_ptr
weak_ptr
kullandığım zaman? unique_ptr
kullanmanın bir yolu yok mu? Çoğu durumda shared_ptr
çok küçük bir kapsamda bir işaretçi kullanarak olmadığım sürece daha mantıklı gibi görünüyor bana?
class Device {
};
class Settings {
std::shared_ptr<Device> device;
public:
Settings(std::shared_ptr<Device> device) {
this->device = device;
}
std::weak_ptr<Device> getDevice() {
return device;
}
};
int main() {
std::shared_ptr<Device> device(new Device());
Settings settings(device);
// ...
std::weak_ptr<Device> myDevice = settings.getDevice();
// do something with myDevice...
}
Bu gitmek için bir yoldur? Çok teşekkür ederim!
CEVAP
unique_ptr
getDevice()
yüzünden işe yaramaz bir değil mi?
Hayır, şart değil. Burada önemli olan uygun belirlemektirmülkiyet politikasıDevice
nesne için, yani nesne (akıllı) işaretçi tarafından işaret sahibi olacak.
Settings
nesne örneği olacakyalnız? Device
nesne Settings
nesne yok olduğunda otomatik olarak yok olacak, ya da o nesne daha uzun yaşamak gerekir?
İlk durumda, std::unique_ptr
ne ihtiyacın var, o zaman yapar Settings
tek (benzersiz) sahibi olan sivri uçlu bir nesne ve tek nesne olan sorumludur yıkımı.
, getDevice()
bu varsayım altında dönmesi gereken basitgözlemleyerekpointer (işaretçiler gözlem sivri nesne yaşatmak olan işaretçiler). Gözlem işaretçi basit tür ham bir işaretçi
#include <memory>
class Device {
};
class Settings {
std::unique_ptr<Device> device;
public:
Settings(std::unique_ptr<Device> d) {
device = std::move(d);
}
Device* getDevice() {
return device.get();
}
};
int main() {
std::unique_ptr<Device> device(new Device());
Settings settings(std::move(device));
// ...
Device *myDevice = settings.getDevice();
// do something with myDevice...
}
[NOT 1:Herkes çiğ göstericiler kötü, güvensiz ve tehlikeli olduğunu söyleyip duruyor zaman burada ham işaretçi kullanarak, ben neden merak ediyor olabilirsiniz. Aslında, o değerli bir uyarıdır, ama önemli olan doğru cümleyi Tamamla: ham işaretçiler kötümanuel bellek yönetimi gerçekleştirmek için kullanılıryani ayrılırken ve ayırmayı kaldırma nesneleri new
delete
. Kullanılan saf olarak elde etmek için başvuru anlambilim ve etrafa dağıtın olmayan sahibi, gözlem işaretçileri, hiçbir şey yok özünde tehlikeli ham göstericiler, dışında belki de aslında bir " özen değil başvuru sarkan bir işaretçi.-NOT 1 END]
[NOT 2:Yorum çıktı, mülkiyeti eşsiz bulunduğu bu özel durumdavesahip olunan nesne her zaman garantili mevcut olması (yani iç veri üyesi device
asla olacak nullptr
), fonksiyonu getDevice()
olabilir (belki) geri dönmek yerine, bir başvuru işaretçisi. Süre bu doğruysa, karar verdim dönmek bir ham işaretçi çünkü burada demek istediğim bu bir kısa cevap diye bir genelleme yapmak durumda device
olabilir nullptr
ve gösteren ham öğelerdir TAMAM sürece kimse kullanmaz onlar için manuel bellek yönetimi.-NOT 2 END]
Bu durum ise Settings
nesne olursa kökten farklı, tabii kideğilcihazın özel mülkiyet var. Bu Settings
nesne imha Device
sivri nesne imha da ima etmeli yoksa bu durumda, örneğin olabilir.
Bu programın bir tasarımcı olarak sana söyleyebileceğim tek şey; verdiğiniz örnek, benim bu durumda olup olmadığını söylemek zordur.
Sana yardım etmek için bir yolunu bul, diye sorabilirsiniz kendinize verip diğer nesneleri dışında Settings
o hakkım devam et Device
nesne hayatta olduğu sürece tuttukları bir işaretçi için, yerine sadece pasif bir gözlemci. Eğer bu gerçekten böyleyse, o zaman gerekirhisseli mülkiyet politikasıstd::shared_ptr
veren:,
#include <memory>
class Device {
};
class Settings {
std::shared_ptr<Device> device;
public:
Settings(std::shared_ptr<Device> const& d) {
device = d;
}
std::shared_ptr<Device> getDevice() {
return device;
}
};
int main() {
std::shared_ptr<Device> device = std::make_shared<Device>();
Settings settings(device);
// ...
std::shared_ptr<Device> myDevice = settings.getDevice();
// do something with myDevice...
}
weak_ptr
dikkat edin,gözlemleyerekişaretçi, pointer sahibi olmak bir diğer deyişle, Eğer sivri nesne tüm diğer sahibi işaretçiler kapsam dışına çıktığında sivri nesne canlı tutmak değildir.
Normal bir raw üzerinde gösterici weak_ptr
avantajı güvenli bir şekilde weak_ptr
olup olmadığını anlayabilirsinizsarkanya da geçerli bir nesneye işaret olup olmadığını, ya da eğer nesne ilk işaret, yani yok edildi). Bu expired()
üye weak_ptr
nesne işlevini çağırarak yapılabilir.
Python: sınıf baskı kullanarak bir sın...
Nasıl bir dosya a 'akıllı' ş...
Java kullanarak.net.Ateş ve işlemek iç...
Nasıl iPhone için Windows geliştirme m...
Dinamik hücre düzenleri için UİTableVi...