Hi all,
I'm gradually starting to make this transition from the world of C to C++, and now that I have a little progress, I have some things that are still a bit confusing to me. One of them is if I nest a class inside another class. If I'm inside the nested class, does "this" point to the nested class or the wrapper class? Likewise, what if I want to refer to one and the other separately. Can I get both this 's? If so, I suppose I could only do that from inside the nested class or else how would it know which instance of the nested class to get it from?...
Thanks,
Sean

Dani AI

Generated

Short answer: inside a nested class member function, this points to the nested-class instance, not to any enclosing-class instance. A nested class in C++ is just a type declared in the scope of the outer class — it does not automatically carry a back-pointer to the particular outer object. That explains the two different addresses printed: the outer object and the inner/member subobject live at different addresses (offsets depend on layout/alignment).

As said, nesting is about scope, not implicit association. As suggested, the usual ways to let a nested object access its enclosing object are:

  • give the nested object an explicit pointer/reference to the outer object (constructed or set by the outer), or
  • pass the outer object into the nested methods when needed, or
  • make appropriate friend declarations or accessors if private members must be accessed.

Example (pointer approach — different from earlier examples in the thread):

#include <iostream>

class Outer {
public:
  int value;
  class Inner {
  public:
    Outer* parent;
    Inner(Outer* p) : parent(p) {}
    void show() const { std::cout << "parent->value = " << parent->value << '\n'; }
  } inner;

  Outer(int v) : value(v), inner(this) {}
};

int main() {
  Outer o(42);
  o.inner.show();
}

Notes and cautions: passing this to initialize a member is legal, but the outer object is still under construction — avoid using uninitialized parts or virtual dispatch. If lifetime/ownership matters, prefer smart-pointer patterns (with enable_shared_from_this) or pass the parent into methods rather than storing raw pointers. The low-level tricks that compute the outer address from a member pointer (the container_of/offsetof technique) only work for standard-layout types and are fragile; prefer explicit references for clarity and safety. For the language rule on nested types see cppreference: nested types.

Recommended Answers

All 5 Replies

If you have composition, then the this refers to whichever "object" the current function is a member of.

class A {
 private:
   int somePrvInt;
 public:
   A() : somePrvInt(0) {}
   int getPrvInt() {
     return this->somePrvInt;
     // this refers to the current A object
   }
   
};

class B {
 private:
   A somePrvA;
 public:
   B() {}
   A getPrvA() {
     return this->somePrvA;
     // this refers to the current B object
   }
   int getPrvAPrvInt() {
     return this->somePrvA.getPrvInt();
     // this still refers to the current B object
   }
};

If you have inheritance, in the base class, this refers to just the base class, in the derived class it refers to both simultaneously. This is what allows you direct access to the protected (but not private) members of A from inside B.

class A {
 protected:
   int someProtInt;
 public:
   A(int newInt = 0) : someProtInt(newInt) {}
   virtual int getSomeProtInt() {
     return this->someProtInt;
     // this refers to the A part of the current B:A object
   }
   
};

class B : public A {
 public:
   B(int newAInt = 0) : A(newAInt) {}

   int getSomeProtInt() {  //overrides A::getSomeProtInt()
     return this->someProtInt
     // this refers to both the current B : A object
   }
};

: you covered two good cases, but none are about the OP's question.

If you have a nested class, then the this pointer, within a call to a member of the nested class, refers to an instance of the nested class (not its wrapper class). However, the nested class has the advantage that it has potential access to all the methods and members of its wrapper. If you want access to both the nested class and the wrapper class, here's the usual trick: (and I put some const, as a wink to your previous posts ;) )

#include <iostream>

class Wrapper {
  private:
    int value;
 
    void bar() const {
      std::cout << "The answer is " << value << std::endl;
    };
 
  public:
    class Nested {
      private:
        Wrapper& Parent;
      public:
        Nested(Wrapper& aParent) : Parent(aParent) { };
        void foo() const {
          Parent.bar();
        };
    };
    Wrapper(int aValue) : value(aValue) { };
};

int main() {
  Wrapper A(42);
  Wrapper::Nested B(A);

  std::cout << "What is the answer to the ultimate question of life, the universe, and everything?" << std::endl;
  B.foo();
};

Ok, in that case, Parent is a member that gets a constructor call, so that makes sense, but how about in this case where the constructor is separate but seemingly related by nesting, but maybe not anyway:

#include <iostream>
class Wrapper 
{
public:
  int valueW;
  void bar() 
  {
    std::cout << "The answer is this->valueW = " << this->valueW <<", this->nest.valueN = "<<this->nest.valueN << ", this = "<<this<<std::endl;
    std::cout <<"this->nest.foo() = "<<std::endl;
    this->nest.foo();
  };
  class Nested 
  {
  public:
  int valueN;
    Nested(int v):valueN(v)
    {
    }
    void foo() 
    {
      std::cout <<"valueN = "<<valueN<<", this = "<<this<< std::endl;
      std::cout <<"however, I exist inside of a Wrapper but do I really not know which Wrapper::this, this is inside of on my own? "<<std::endl;
    };
  };
    Nested nest;
  Wrapper(int aValue) : valueW(aValue),nest(aValue-10)
  { 
    
  };
};
int main()
{
  Wrapper A(42);
  std::cout << "What is the answer to the ultimate question of life, the universe, and everything?" << std::endl;
  A.bar();
};

What is the answer to the ultimate question of life, the universe, and everything?
The answer is this->valueW = 42, this->nest.valueN = 32, this = 0x7fff5fbff680
this->nest.foo() =
valueN = 32, this = 0x7fff5fbff684
however, I exist inside of a Wrapper but do I really not know which Wrapper::this, this is inside of on my own?

I think you are getting confused. Think of the Nested class as a class of its own. The
only difference is its scope. You can only access it from the outer class. The nested
class has no association with the parent class, besides the scope resolution.

What you are doing is creating a instance of Nested class in the Wrapper class.
Therefore every different instance of wrapper will have different instance of Nested.

Ah, got it--scope... I thought somehow they were the same class.

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.