una resueltos que programacion orientada objetos metodos metodo ejercicios ejemplos codigo clases clase c++ class constructor

c++ - resueltos - Creando una instancia de clase



que es un metodo en programacion (3)

¿Cuál es la diferencia entre las líneas 1, 2, 3, 4?

¿Cuándo uso cada uno?

¿Por qué la línea 3 imprime el constructor Foo y la línea 7 devuelve un error y la línea 8 no?

#include <iostream> using namespace std; class Foo { public: Foo ( ) { cout << "constructor Foo/n"; } }; class Bar { public: Bar ( Foo ) { cout << "constructor Bar/n"; } }; int main() { /* 1 */ Foo* foo1 = new Foo (); /* 2 */ Foo* foo2 = new Foo; /* 3 */ Foo foo3; /* 4 */ Foo foo4 = Foo::Foo(); /* 5 */ Bar* bar1 = new Bar ( *new Foo() ); /* 6 */ Bar* bar2 = new Bar ( *new Foo ); /* 7 */ Bar* bar3 = new Bar ( Foo foo5 ); /* 8 */ Bar* bar3 = new Bar ( Foo::Foo() ); return 1; }


  1. Asigna una memoria dinámica de la tienda gratuita y crea un objeto en esa memoria utilizando su constructor predeterminado. Nunca lo borras, entonces la memoria se pierde.
  2. Hace exactamente lo mismo que 1; en el caso de los tipos definidos por el usuario, los paréntesis son opcionales.
  3. Asigna una memoria automática y crea un objeto en esa memoria usando su constructor predeterminado. La memoria se libera automáticamente cuando el objeto se sale del alcance.
  4. Similar a 3. En teoría, el objeto nombrado foo4 se inicializa por defecto: construye, copia y destruye un objeto temporal; generalmente, esto se elimina dando el mismo resultado que 3.
  5. Asigna un objeto dinámico, luego inicializa un segundo copiando el primero. Ambos objetos se filtraron; y no hay forma de eliminar el primero ya que no lo mantiene puntero.
  6. Hace exactamente lo mismo que 5.
  7. No compila Foo foo5 es una declaración, no una expresión; los argumentos de función (y constructor) deben ser expresiones.
  8. Crea un objeto temporal e inicializa un objeto dinámico copiándolo. Solo se filtra el objeto dinámico; el temporal se destruye automáticamente al final de la expresión completa. Tenga en cuenta que puede crear el temporal solo con Foo() lugar del equivalente Foo::Foo() (o incluso Foo::Foo::Foo::Foo::Foo() )

¿Cuándo uso cada uno?

  1. No, a menos que quieras decoraciones innecesarias en tu código.
  2. Cuando desee crear un objeto que sobreviva al alcance actual. Recuerde eliminarlo cuando haya terminado con él, y aprenda a usar punteros inteligentes para controlar la vida útil de manera más conveniente.
  3. Cuando quiere un objeto que solo existe en el alcance actual.
  4. No, a menos que piense que 3 parece aburrido y qué agregar una decoración innecesaria.
  5. No, porque pierde la memoria sin posibilidad de recuperación.
  6. No, porque pierde la memoria sin posibilidad de recuperación.
  7. No, porque no compilará
  8. Cuando desee crear una Bar dinámica desde un Foo temporal.

Las líneas 1,2,3,4 llamarán al constructor predeterminado. Son diferentes en esencia ya que 1,2 es un objeto creado dinámicamente y 3,4 son objetos creados estáticamente.

En la línea 7, creas un objeto dentro de la llamada de argumento. Entonces es un error.

Y las líneas 5 y 6 son una invitación a la pérdida de memoria.


/* 1 */ Foo* foo1 = new Foo ();

Crea un objeto de tipo Foo en la memoria dinámica. foo1 señala. Normalmente, no usaría punteros crudos en C ++, sino un puntero inteligente. Si Foo fuera un tipo de POD, esto llevaría a cabo la inicialización del valor (no se aplica aquí).

/* 2 */ Foo* foo2 = new Foo;

Idéntico a antes, porque Foo no es un tipo de POD.

/* 3 */ Foo foo3;

Crea un objeto Foo llamado foo3 en el almacenamiento automático.

/* 4 */ Foo foo4 = Foo::Foo();

Utiliza la inicialización de copia para crear un objeto Foo llamado foo4 en el almacenamiento automático.

/* 5 */ Bar* bar1 = new Bar ( *new Foo() );

Utiliza el constructor de conversión de Bar para crear un objeto de tipo Bar en el almacenamiento dinámico. bar1 es un puntero a él.

/* 6 */ Bar* bar2 = new Bar ( *new Foo );

Igual que antes.

/* 7 */ Bar* bar3 = new Bar ( Foo foo5 );

Esta es solo una sintaxis inválida. No puedes declarar una variable allí.

/* 8 */ Bar* bar3 = new Bar ( Foo::Foo() );

Funcionaría y funcionaría con el mismo principio en 5 y 6 si no se declarase bar3 en 7.

5 y 6 contienen fugas de memoria.

Sintaxis como new Bar ( Foo::Foo() ); no es usual Suele ser un new Bar ( (Foo()) ); - cuenta de paréntesis extra para el análisis más irritante. (corregido)