2013-11-04 9 views
6

Scavando in un progetto C++, ho incontrato un uso strano di new dell'operatore C++ s ':Strano C++ nuovo utilizzo dell'operatore

int arr[5]; 
ClassA* a = new(arr) ClassA(); 

La prego quindi di aiutarmi a capire questa sintassi?

+5

google "posizionamento nuovo" o vedere questa domanda: http://stackoverflow.com/questions/222557/what-uses-are-there-for -placement-new – Kos

+0

@Askyane Ho incluso un breve riassunto e un link per il tuo esame – GMasucci

risposta

2

È la nuova sintassi del posizionamento: consente di creare un oggetto nella posizione puntata nella memoria. Prendere in considerazione un uso "normale" di nuovo:

X *p = new X; 
... 
delete p; 

È possibile ottenere lo stesso effetto facendo:

#include <new> 

... 

void *buffer = ::operator new(sizeof(X)); 
X *p = new (buffer) X; 
... 
p->~X(); 
::operator delete(buffer); 

Quest'ultimo alloca memoria sufficiente per contenere un X (senza costruire un X in esso), quindi costruisce esplicitamente uno X nella memoria allocata. Successivamente, distrugge esplicitamente lo X creato e quindi rilascia la memoria che lo conteneva.

Vedere anche la Domanda C++: http://www.parashift.com/c++-faq/placement-new.html

2

L'operatore new() può prendere una size (dimensione in byte) nothrow_value (restituisce un puntatore nullo anziché un'eccezione bad_alloc) o pointer (costruire l'oggetto nella memoria già allocata puntato da questo puntatore) argomento, e nell'uso che descrivi sta creando un nuovo oggetto nella posizione di memoria indicata da arr. Per una guida decente su di esso vorrei guardare this link.

Nel caso in cui si citata che sta usando il puntatore per arr per creare la sua nuova istanza di ClasseA in.

2

Questa sintassi si chiama la sintassi placement new. In genere viene utilizzato per costruire un oggetto su un buffer preassegnato. Ciò è utile quando si costruisce un pool di memoria, un garbage collector o semplicemente quando le prestazioni e la sicurezza delle eccezioni sono di primaria importanza (non c'è pericolo di errori di allocazione poiché la memoria è già stata allocata e la costruzione di un oggetto su un buffer preassegnato richiede meno tempo) .

char *buf = new char[sizeof(string)]; // pre-allocated buffer 
string *s1 = new (buf) string("test1"); // placement new 
string *s2 = new string("test2"); //ordinary new 

Quando si tratta di deallocazione, non c'è placement delete che fa automaticamente la magia. Non dovresti deallocare ogni oggetto che sta usando il buffer di memoria. Invece si dovrebbe distruggere ogni oggetto manualmente, quindi cancellare [] solo il buffer originale

+2

Penso che volevi distruggere manualmente ogni oggetto e quindi eliminare il buffer originale, non viceversa. –

+1

@StuartGolodetz scusa per quello stupido errore. corretto – jester