Digamos que tengo dos objetos locales. Cuando la función retorna, ¿se garantiza cuál saldrá primero del alcance?Orden y punto de llamada destructor
Por ejemplo:
tengo una clase como esta:
class MutexLock
{
/* Automatic unlocking when MutexLock leaves a scope */
public:
MutexLock (Mutex &m) { M.lock(); }
~MutexLock(Mutex &m) { M.unlock(); }
};
Este es un truco muy común que se utiliza para liberar automáticamente la exclusión mutua cuando se va fuera de alcance. Pero, ¿y si necesito dos mutexes en el alcance?
void *func(void *arg)
{
MutexLock m1;
MutexLock m2;
do_work();
} // m1 and m2 will get unlocked here. But in what order? m1 first or m2 first?
Esto realmente no puede causar ningún punto muerto. Pero puede haber instancias en las cuales el orden de liberación del recurso pueda ser útil para el usuario. En ese caso, ¿es importante ser explícito en lugar de confiar en los destructores?
Además, ¿puede la destrucción ser retrasada por el compilador en cualquier caso? Lo que quiero decir es
func()
{
{
foo f();
} ---------> Can compiler choose to not destroy f here, rather do it at the time when func() is returning.
}
Para sustentar la primera parte de la respuesta de @aix, este es un extracto del estándar (versión preliminar, Fecha: 2006-11-06 --- este aspecto no ha cambiado en versiones posteriores. Las referencias a las secciones se omiten para mayor claridad): "Al salir de un ámbito (no importa cuán logrado), se invocan destructores para todos los objetos construidos con duración de almacenamiento automático (objetos nombrados o temporales) que se declaran en ese ámbito, en el orden inverso al de su declaración". Por supuesto, su ejemplo implica declaraciones de variables automáticas. – sturmer