2009-12-01 11 views
10

Estoy confundido con la palabra clave this en C++, no estoy seguro de que si estoy haciendo lo correcto pasando this. Aquí está la pieza de código que estoy luchando con:cómo pasar "esto" en C++

ClassA::ClassA(ClassB &b) { 

    b.doSth(this); 
    // trying to call b's routine by passing a pointer to itself, should I use "this"? 
} 

ClassB::doSth(ClassA * a) { 
     //do sth 
} 
+0

cuando "sí" en ese comentario, ¿te refieres al objeto ClassA o al objeto ClassB? – Stobor

+1

¿Cuál es exactamente tu pregunta? ¿Qué esperas y qué estás obteniendo? – fserb

+0

¿Tiene alguna pregunta o solo compartió? –

Respuesta

2

En este caso utilizando this va a pasar un puntero a la clase de persona que llama, que es A, a b.DoSth. Parece que lo estás haciendo bien. La palabra clave this siempre apunta a la instancia de clase desde la que la está utilizando.

8

En C++, this es una palabra clave que se define como "el puntero a la instancia de objeto actual". Entonces tu código de arriba es correcto.

Dependiendo de la relación de herencia/composición entre ClassA y ClassB, probablemente hay mejores maneras de lograr lo que está haciendo que usando el puntero this.

0

this es un puntero a la instancia del objeto, por lo que lo que está haciendo es correcto.

Lea this para obtener más información.

0

this es un puntero constante para su propio objeto. this puntero no modificable.

ClassA::ClassA(ClassB &b) { 

     b.doSth(this); 
     // here 'this' refers to this object ie the instance of ClassA. 
     // When you pass 'this' to doSth function --> is equivalent to passing 
     // the instance of current object of ClassA. 
     // 
    } 
14

Lo está utilizando correctamente. Este puntero apunta a la instancia del objeto actual.

class helper 
{ 
public: 
    void help(worker *pWorker) { 
      //TODO do something with pWorker . . . 
    } 

    void help2(worker& rWorker) { 
      //TODO do something with rWorker . . . 
    } 
}; 

class worker 
{ 
public: 
    void dowork() { 
      //this one takes a worker pointer so we can use the this pointer. 
      helper.help(this); 

      //to pass by reference, you need to dereference the this pointer. 
      helper.help2(*this); 
    } 
    helper helper; 
}; 

También digamos que declara worker *pW = new worker(). Si llama a uno de los métodos (dowork) en el objeto pW, verá que el puntero this y pW tienen exactamente el mismo valor (ambos son la misma dirección).

(no lo he probado para asegurarme de que se crea, pero creo que debería).

5

Está perfectamente bien pasar 'esto' o '* esto' como lo está haciendo.

Peligros

por vida:

Un punto sobre el ejemplo que ha suministrado es que usted está llamando doSth desde el constructor de ClassA. El objeto que se pasa a doSth es posiblemente un objeto parcialmente construida:

class ClassC { 
public: 
    ClassC() 
    : m_c() 
    {} 
    int m_c; 
}; 

class ClassA : public ClassC { 
public: 
    ClassA (ClassB & b) 
    : ClassC() 
    , m_b (b.doSth (this)) // ClassC constructed 
          // ClassA members partially init. 
    { 
    b.doSth (this);   // ClassA members initialized 
    } 

    // ... 
    int m_a; 
}; 

class ClassD : public ClassA { 
public: 
    ClassD(ClassB & b) 
    : ClassA (b)    // Partially init 
    , m_d() 
    { 
          // ClassC and ClassA constructed 
          // ClassD members initialized 
    } 
    int m_d; 
}; 

Puede haber problemas si doSth utiliza miembros que aún no han sido inicializados:

void ClassB::doSth (ClassA * a) { 
    int i = a->m_c;  // OK m_c is initialized 

    int j = a->m_a;  // Not OK, m_a not initialized when called 
         // from member initialization list. 

    int k = static_cast<ClassD*> (a).m_d; // Not OK 
} 

Utilizando el tipo dinámico del objeto :

Por último, cualquier uso del tipo dinámico del objeto (por ejemplo, llamadas virtuales, dynamic_cast, typeid) tendrá resultados diferentes en un partial y objeto construido que en un objeto completo (y en algunos casos puede tener un comportamiento indefinido).

void ClassB::doSth (ClassA * a) { 
    if (ClassD * d = dynamic_cast<ClassD *> (a)) 
    { 
    // Never true when called from ClassA::ClassA 
    } 
} 
Cuestiones relacionadas