0

Objects in heap?

Dog Lessie = new Dog(); I created an instance of the Dog class in the dynamic memory. As I know, all of its members are stored next to each other. But when I declare a pointer as a member of the Dog class like: class Dog { public: Dog() { age = new int(2); } private: int *age; }; the memory cell where the *age points, can be anywhere in the heap. Then the question is why should I declare a pointer member like this? age will be in heap if I declare it as integer, because of "new Dog()".

21st Nov 2016, 3:06 PM
Marcell Juhasz
1 Resposta
+ 1
Firstly: note if you declare an object (not only on the heap - this apply to stack too) the data members will be "next" to each other, but there may be gaps between them. For example: class Dog { int weight; char name[13]; int age; } There may be some "dead" space between name and age in memory as the compiler will attempt to place int's on WORD boundaries (typically 4 bytes on 32 bit and 8 bytes on 64bits for int's) and, since the 13 bytes of name will cause misalignment, the compiler will "pad" 3 bytes before placing the age member. You can control this (to some degree) by #pragma pack(...) [this is for VC++; not sure how portable this is] and, since C++11, with alignof/ alignas (which is portable). Secondly, about your question: you are right, the int *age pointer will be inside the memory layout of your class, but the actual memory it points to will be in a different part of the heap. This is by design and is how it is intended to work. If it did not work this way and if the compiler could somehow re-allocate space inside your class layout in memory, then sizeof(Dog) would give you different answers depending on 'if' and 'how much' memory was allocated for age. If you think about it - your class contains a pointer (plus other data members we'll ignore for now). It should not matter where or how many bytes it points to. Lastly, why should you declare a pointer like this? Your example is not very good and, yes, you would not allocate memory on the heap for the age of the dog. You will simply have a member 'int dog;' since a dog cannot have more than one age, so an array or pointer is unnecessary. But imagine you need to track the weight of your dog continuously for the last 12 months. You could do something like this: class Dog { public: Dog(){weightRec = new int[12];} ~Dog(){delete []weightRec;} int* weightRec; void weighDog(int w) { for(int i = 10; i >= 0; i--) weightRec[i+1] = weightRec[i]; weightRec[0] = w; }
13th Dec 2016, 6:09 PM
Ettienne Gilbert
Ettienne Gilbert - avatar