2010-03-05 17 views
5

Ho un caso in cui desidero memorizzare un elenco di risorse in un vettore std ::. Come la vedo io, le mie opzioni sono le seguenti:RAII e C++ STL

  1. dare il mio risorsa un costruttore di default
  2. memorizzarli come oggetti mucchio (e avvolgerli in un puntatore in comune)

Opzione 1 rende possibile costruire risorse non valide e l'opzione 2 mi obbliga a usare l'heap.

Mi mancano alcune opzioni qui?

+1

perché si desidera assegnare il nome predefinito delle risorse? il vettore richiede solo il copyctor. – Naveen

+2

"l'opzione 2 mi obbliga ad usare l'heap" - beh, il vettore memorizzerà anche i suoi contenuti nell'heap (a meno che non si utilizzi un allocatore personalizzato), anche se nella memoria contigua. Quindi non sarai in grado di ignorare l'utilizzo dell'heap in un modo o nell'altro. –

+0

ha rilevato che stavo memorizzando un riferimento nella mia risorsa, quindi il problema non era il costruttore predefinito, ovvero – dirk

risposta

7

Non è necessario un costruttore predefinito per avere un vettore di istanze.

L'unica limitazione è che non è possibile utilizzare vector :: ridimensionare con l'argomento predefinito quando la classe non ha un costruttore predefinito.

vec.resize(20); // requires default constructor 

ma si può dare vector :: ridimensionare un oggetto predefinito:

std::vector<foo> vec; 
vec.resize(20, foo(10)); // give a sample object since foo has not default constructor 
1

È possibile memorizzare gli oggetti con constuctor non banale nel vettore. L'archivio degli oggetti in contenitori stl dovrebbe avere una semantica di assegnazione (copia costruttore e assegnazione operatore).

1

Una terza opzione sarebbe quella di utilizzare Boost.PointerContainer. Tuttavia, gli oggetti saranno ancora allocati individualmente sullo heap. Come ha commentato Johann, std :: vector utilizza già l'heap per archiviare oggetti (in modo contiguo), quindi non c'è modo di evitare completamente l'heap.

Spesso non ha senso consentire alle risorse (come mutex, flussi I/O, ecc.) Di avere semantica della copia. Pertanto, devono essere resi non copiabili rendendo privato il costruttore di copia e l'operatore di assegnazione. Sfortunatamente, la restrizione non copiabile rende impossibile memorizzare direttamente le risorse come valori all'interno dei contenitori STL. È quindi necessario ricorrere a Boost.PointerContainer o contenitori di puntatori intelligenti. La sezione motivazione della documentazione di Boost.PointerContainer spiega perché preferiresti usarne uno sull'altro.