-
Data: 2009-08-02 12:09:39
Temat: Re: [c++]Prosta klasa, czemu nie wywołuje destruktorów?
Od: Bronek Kozicki <b...@s...net> szukaj wiadomości tego autora
[ pokaż wszystkie nagłówki ]P.K.D wrote:
> Tutaj ta klasa: http://paste.dprogramming.com/dpibqklz
>
> Chodzi o to, że gdy wywołuję server::clearList() to obiekty nie są
> niszczone, chyba dlatego, że lista zawiera wskaźniki. Jak to zrobić i
> czy da się zrobić tak, że destruktory będą wywoływane automatycznie?
1. żeby wiedzieć kiedy będą wołane destruktory, najlepiej polegać na
jakimś sprytnym wskaźniku oraz wiedzieć kto kiedy jest właścicielem
obiektu. Poniżej stosuję boost::shared_ptr (bo bardziej popularny i
obsługuje klasy niekompletne), ale równie dobrze możesz stosować coś
innego. "dzielenie własności" wbrew nazwie "shared" jest tutaj potrzebne
tylko do zapewnienia semantyki płytkiego kopiowania i do niczego więcej
- boost::intrusive_ptr czy własne wynalazki w tej roli też się sprawdzą.
2. skoro już masz zagwarantowane wyłanie destruktora, to martw się o
notyfikację obiektu który trzyma listę obiektów żeby je z tej listy
skasował. Ja korzystam z funkcji UnregisterMyClass wołanej z
destruktora. Jedyny wyjątek kiedy tego nie trzeba robić - wtedy kiedy
lista jest i tak w całości kasowana. Oczywiście "lista" jest umowna -
rownie dobrze może być mapa albo jakaś własna, bardziej złożona
struktora. Ja w przykładzie niżej korzystam z std::list , dla zachowania
jasności.
3. do tego wszystkiego idealnie pasuje Pimpl, bo daje tanią samantykę
kopiowania i jednoznaczną własność wskaźnika. Jeżeli nie wiesz co to
jest : http://www.gotw.ca/publications/mill04.htm
Poniżej przykładowy kod.
// creator.hpp
class MyClass
{
class Impl;
boost::shared_ptr<Impl> pimpl_;
// zwiększamy ekapsulacje ograniczajac dostep do c-tora
friend class Creator;
explicit MyClass (boost::shared_ptr<Impl> p) : pimpl_(p) {}
public:
// opcjonalnie takie dwie funkcje, jeżeli potrzebne
void Unregister();
bool IsRegistered() const;
// dalej typowy Pimpl
// ...
};
class Creator
{
// zwiekszamy enkapsulacje ograniczajac dostep do UnregisterMyClass
friend class MyClass;
void UnregisterMyClass(const MyClass::Impl& my);
std::list<const MyClass::Impl*> myclassobjects_;
// ... może być więcej podobnych kolekcji ...
public:
~Creator();
MyClass MakeMyClass(parametry konstruktora);
// ...
};
// creator.cpp
#include "creator.hpp"
class MyClass::Impl : public IMogeSobieDziedziczycCokolwiek
// noncopyable - bo nie obiecujemy więcej niż musimy zaimplementować
, boost::noncopyable
{
Creator& creator_;
bool registered_;
// ...
public:
Impl(Creator& c, parametry konstruktora)
: creator_(c)
, registered_(true)
// ... inicjalizacja innych pól, definicja konstruktora
~Impl() {Release(true);}
void Release(bool unregister)
{
if (unregister && registered_)
{
creator_.UnregisterMyClass(*this);
registered_ = false;
}
}
// opcjonalnie takie dwie funkcje
void Unregister() {Release(true);}
bool IsRegistered() const {return registered_;}
// dalej typowy Pimpl
// ...
};
bool MyClass::IsRegistered() const {return pimpl_->IsRegistered();}
void MyClass::Unregister() {pimpl_->Unregister();}
// dalej typowy Pimpl, tzn podobnie jak IsRegistered i Unregister
// ...
// ...
// zarządzanie kolekcja obiektów MyClass przez klasę Creator :
void Creator::UnregisterMyClass(const MyClass::Impl& my)
{
myclassobjects_.remove(&my);
};
MyClass Creator::MakeMyClass(parametry konstruktora)
{
boost::shared_ptr<MyClass::Impl> p(new MyClass::Impl(*this,
parametry konstruktora));
// Nie trzymamy MyClass::Impl na własność - przekazujemy do MyClass !
myclassobjects_.push_back(p.get());
return MyClass(p);
}
Creator::~Creator()
{
// Kazemy obiektom MyClass::Impl sie "zwolnić", zeby oszczędzić
// wołanie UnregisterMyClass z destruktorów
std::for_each(myclassobjects_.begin(), myclassobjects_.end(),
boost::bind(&MyClass::Impl::Release, _1, false));
myclassobjects_.clear();
}
I jeszcze jedna uwaga - NIE NADUŻYWAĆ , bo nie jest wcale takie proste.
Ale jest za to dosyć niezawodne - jeżeli potrzebujemy mieć kolekcję
obiektów które skonstruowaliśmy.
B.
--
Remove -trap- when replying. Usun -trap- gdy odpisujesz.
Najnowsze wątki z tej grupy
- Na grupie comp.os.linux.advocacy CrudeSausage twierdzi, że Micro$lop używa SI do szyfrowania formatu dok. XML
- Błąd w Sofcie Powodem Wymiany 3 Duńskich Fregat Typu Iver Huitfeldt
- Grok zaczął nadużywać wulgaryzmów i wprost obrażać niektóre znane osoby
- Can you activate BMW 48V 10Ah Li-Ion battery, connecting to CAN-USB laptop interface ?
- We Wrocławiu ruszyła Odra 5, pierwszy w Polsce komputer kwantowy z nadprzewodzącymi kubitami
- Ada-Europe - AEiC 2025 early registration deadline imminent
- John Carmack twierdzi, że gdyby gry były optymalizowane, to wystarczyły by stare kompy
- Ada-Europe Int.Conf. Reliable Software Technologies, AEiC 2025
- Linuks od wer. 6.15 przestanie wspierać procesory 486 i będzie wymagać min. Pentium
- ,,Polski przemysł jest w stanie agonalnym" - podkreślił dobitnie, wskazując na brak zamówień.
- Rewolucja w debugowaniu!!! SI analizuje zrzuty pamięci systemu M$ Windows!!!
- Brednie w wiki - hasło Dehomag
- Perfidne ataki krakerów z KRLD na skrypciarzy JS i Pajton
- Instytut IDEAS może zacząć działać: "Ma to być unikalny w europejskiej skali ośrodek badań nad sztuczną inteligencją."
- Instytut IDEAS może zacząć działać: "Ma to być unikalny w europejskiej skali ośrodek badań nad sztuczną inteligencją."
Najnowsze wątki
- 2025-08-06 Gdynia => Konsultant wdrożeniowy (systemy controlingowe) <=
- 2025-08-06 Białystok => Inżynier oprogramowania .Net <=
- 2025-08-06 "[...] sejmowe wystąpienie posłanki Klaudii Jachiry, która zakończyła je słowami ,,Sława Ukrainie"."
- 2025-08-05 "Chiny przekraczają w wydobyciu 4 mld ton węgla, Indie i USA ponad 1 mld, a Rosja 500 mln ton [...]"
- 2025-08-05 Panuje się 181 159,42 zł./mies. na posła w 2026r.
- 2025-08-05 "Chiny przekraczają w wydobyciu 4 mld ton węgla, Indie i USA ponad 1 mld, a Rosja 500 mln ton [...]"
- 2025-08-05 Czy cos fi przechodzi przez trafo separujące?
- 2025-08-05 kajaki i promile
- 2025-08-05 Re: Tesla jest bezpieczna, wczoraj spaliła się doszczętnie na Ursynowie i nikomu się nic nie stało
- 2025-08-05 Gdynia => Przedstawiciel handlowy / KAM (branża TSL) <=
- 2025-08-05 Re: Atak na lekarza w Oławie. Policja zatrzymała sprawcę na lotnisku Polska Agencja Prasowa 4 sierpnia 2025, 12:16 FACEBOOK X E-MAIL KOPIUJ LINK W szpitalu w Oławie 37-letni pacjent zaatakował lekarza, po tym, jak ten odmówił mu wypisania długoterminowego
- 2025-08-05 B2B i książka przychodów i rozchodów
- 2025-08-04 Re: Atak na lekarza w Oławie. Policja zatrzymała sprawcę na lotnisku Polska Agencja Prasowa 4 sierpnia 2025, 12:16 FACEBOOK X E-MAIL KOPIUJ LINK W szpitalu w Oławie 37-letni pacjent zaatakował lekarza, po tym, jak ten odmówił mu wypisania długoterminowego
- 2025-08-04 Na grupie comp.os.linux.advocacy CrudeSausage twierdzi, że Micro$lop używa SI do szyfrowania formatu dok. XML
- 2025-08-04 Na grupie comp.os.linux.advocacy CrudeSausage twierdzi, że Micro$lop używa SI do szyfrowania formatu dok. XML