Prevent stack allocation for a class AND for derived classes - c++

Is there a way to design a class, that neither it nor its descendants can be allocated automatically (on stack), but only dynamically (in heap)?
I have a 3D scene represented by a scene tree, each object has a parent and a number of children. All scene objects are inherited from some base class SceneObject. I would like to make it impossible to allocate such objects on the stack.
The only way I know to achieve this for a class is to declare a protected constructor and provide a factory (see Is it possible to prevent stack allocation of an object and only allow it to be instantiated with 'new'?). This does indeed work as I want for the class, but not for its descendants. Authors of derived classes need to explicitly declare constructors as non-public and I have no way to control it, thus providing possibilities for an error.
Are there any possibilities to achieve what I want? Any compromises maybe?

Not really, no.
You may be able to screw around with explicitly overriding operator new, or to mix the answer you linked to with templates, but otherwise you're hosed.
I'm going to go off on a limb and guess that your full problem involves resource management; if that's the case, check out the rule of three; if your class has a user-defined destructor, copy constructor, or copy assignment (operator=(const Something&)), you probably need all three.

The only way I know to do this is how your linked answer says - declare the class's constructor as private so nobody but the class itself can create instances of it, and then provide a public static method that creates an instance of the class on the heap. Everyone who wants an instance must call the static method.

Related

Why do references see private members? [duplicate]

I have learned that I can never access a private variable, only with a get-function in the class. But then why can I access it in the copy constructor?
Example:
Field::Field(const Field& f)
{
pFirst = new T[f.capacity()];
pLast = pFirst + (f.pLast - f.pFirst);
pEnd = pFirst + (f.pEnd - f.pFirst);
std::copy(f.pFirst, f.pLast, pFirst);
}
My declaration:
private:
T *pFirst,*pLast,*pEnd;
The access modifiers work on class level, and not on object level.
That is, two objects of the same class can access each others private data.
Why:
Primarily due to efficiency. It would be a non-negligible runtime overhead to check if this == other each time you access other.x which you would have to if the access modifiers worked on object level.
It's also kind of semantically logical if you think of it in terms of scoping: "How big part of the code do I need to keep in mind when modifying a private variable?" – You need to keep the code of the whole class in mind, and this is orthogonal to which objects exist in runtime.
And it's incredibly convenient when writing copy constructors and assignment operators.
IMHO, existing answers do a poor job explaining the "Why" of this - focusing too much on reiterating what behaviour's valid. "access modifiers work on class level, and not on object level." - yes, but why?
The overarching concept here is that it's the programmer(s) designing, writing and maintaining a class who is(are) expected to understand the OO encapsulation desired and empowered to coordinate its implementation. So, if you're writing class X, you're encoding not just how an individual X x object can be used by code with access to it, but also how:
derived classes are able to interact with it (through optionally-pure virtual functions and/or protected access), and
distinct X objects cooperate to provide intended behaviours while honouring the post-conditions and invariants from your design.
It's not just the copy constructor either - a great many operations can involve two or more instances of your class: if you're comparing, adding/multiplying/dividing, copy-constructing, cloning, assigning etc. then it's often the case that you either simply must have access to private and/or protected data in the other object, or want it to allow a simpler, faster or generally better function implementation.
Specifically, these operations may want to take advantage of priviledged access to do things like:
(copy constructors) use a private member of the "rhs" (right hand side) object in an initialiser list, so that a member variable is itself copy-constructed instead of default-constructed (if even legal) then assigned too (again, if legal)
share resources - file handles, shared memory segments, shared_ptrs to reference data etc.
take ownership of things, e.g. auto_ptr<> "moves" ownership to the object under construction
copy private "cache", calibration, or state members needed to construct the new object in an optimally usable state without having to regenerate them from scratch
copy/access diagnostic/trace information kept in the object being copied that's not otherwise accessible through public APIs but might be used by some later exception object or logging (e.g. something about the time/circumstances when the "original" non-copy-constructed instance was constructed)
perform a more efficient copy of some data: e.g. objects may have e.g. an unordered_map member but publicly only expose begin() and end() iterators - with direct access to size() you could reserve capacity for faster copying; worse still if they only expose at() and insert() and otherwise throw....
copy references back to parent/coordination/management objects that might be unknown or write-only for the client code
You can access private members of a class from within the class, even those of another instance.
To understand the answer, I would like to remind you few concepts.
No matter how many objects you create, there is only one copy of one function in memory for that class. It means functions are created only once. However variables are separate for each instance of the class.
this pointer is passed to every function when called.
Now it's because of the this pointer, function is able to locate variables of that particular instance. no matter if it is private of public. it can be accessed inside that function. Now if we pass a pointer to another object of the same class. using this second pointer we will be able to access private members.
Hope this answers your question.
Copy constructor is class' member function and as such has access to class' data members, even those declared as 'private'.
why the man who made that compiler allow this behavior,
that we can see hidden members of an object (that its type is the same of the class where you access the hidden members) in copy constructor or in any method in the class.
The answer: because you when you are in the class that's mean you are the builder or the designer of the class also mean that you know all data members and methods in that class that's why he allow this behavior because you build this class you know every thing about it unlike the users of the class they haven't to know every thing about the class like you.
the idea of hiding data members or method that help the users of this class and not confused them with non important things.
That's it.

abstract classes and constructor in C++

I read this question "C++ Abstract Class: constructor yes or no?" and the answers belonging to it.
But according to answers, I understand that we need the constructor to initialize it data members, however I can use its member functions like setter functions in my derived class to initialize the data members, so Why is it important to define a constructor?
The default constructor definition and the member initializations make the class self contained regarding proper setup conditions (valid state).
Usage of setter methods to manipulate the class instance is optional for class clients (including inheriting classes).
You may consider adding more constructor signatures, that the clients can use to inititialze the class members with a single call, and don't require these applying additional setter calls.
It depends on the particular use case, what's more convenient and semantically correct in the end.
Two reasons:
To ensure the objects are always within a valid state.
You need a copy constructor to ensure that data gets copied correctly (e.g., no blind copies of dynamically allocated resources).
Probably more.

Destructor in class

I have created a class, and according to the textbook Accelerated C++ by Andrew Koenig and Barbara E. Moo,
The work of the destructor is to do any cleanup that should be done whenever an object goes away. Typically this cleanup involves releasing resources, such as memory, that the constructor has allocated.
I am trying to write a destructor, and I'm getting confused by all the code floating out there. Sometimes a simple deconstructor like this is used ~MyIntArray() {} and sometimes there are things between the {}.
What is the rule behind putting things between the curly brackets or not? Is it just containers e.g. lists, arrays, vectors, pointers that need to be placed between the curly brackets (these are the things I see in code examples out there).
edit: this is my class in case that's needed
class msgInfo
{
public:
msgInfo();
msgInfo(int, int, int, std::string, std::list<int>);
private:
int source_id;
int dest_id;
int priority;
std::string payload;
std::list<int> nodePath;
};
Rule 1:
Rule of three in C++03 or rule of five in C++11.
If your class needs a user defined copy constructor or a copy assignment operator then it most likely needs a user defined destructor.
When do you need either of these 3?
When your class has dynamically allocated pointer members and you need to maintain lifetime of each separate from that of another instance member. For e.g: char * member.
When you manage resources. For e.g: Open file handles, mutex locks etc.
Rule 2:
If your class is intended to be used for derivation and you need polymorphic deletion of objects then you must mark the destructor in Base class as virtual.
Well, if you allocated resources dynamically (new etc..) then in the destructor you'd want to release them (delete), in your case, since all of your members are not allocated dynamically, your destructor can be empty ( or non existent).
Another note worth mentioning is, if you do end up implementing the destructor, and you plan on someone inherting your class, you should make it virtual.
It is a good programming practice to provide a destructor in your C++ program even if there is no explicit need for one. In your code you might not have any dynamic memory allocation, so the destructor provided is simply ~MyIntArray() {} without any code inside.
Please also read the Wikipedia article on Rule of Three in C++.
http://en.wikipedia.org/wiki/Rule_of_three_(C%2B%2B_programming)
If you don't provide a destructor, the compiler will provide one for you. This automatically-generator destructor will correctly call the destructors of all of your class's data members, such as payload etc.
If you don't need to do anything beyond that then you don't need to explicitly provide a destructor. Alternatively, an empty one would work equally well.
If, on the other hand, your constructor allocates some resources (for example, connects to a database), then typically you'd need to put some code in your destructor to release that resource (e.g. disconnect from the database). This is the standard C++ idiom used to prevent resource leaks.
Your class does not have any resources that need to be dealt with in the destructor: each type is either built-in (`int) or handles its own resources (std::string,std::list`). So you do not need to implement your own destructor. The compiler will provide one that is equivalent to the empty braces one.
You would need to implement your own if your class had resources that need dealing with: dynamically allocated objects, handles or connections to sockets, databases, reference counts, etc.
One situation where it might make sense to implement an empty destructor is when you have a class which is intended to be derived from and used polymorphically. In this case, a virtual destructor is needed (there are many SO posts about that), and it is common practice to provide an empty implementation so that derived types to not have to implement it themselves when there are no resources to deal with.
virtual ~Foo() {}
A class like this doesn't need a non-trivial destructor (one, with "things between the curly brackets").
In a destructor, you must release resources, you have "manually" allocated. For example:
if you have new/new[] in the constructor and you need to free this memory in the destructor
if you have opened a file in the constructor, close it in the destructor
if you have locked a mutex in the constructor, unlock it in the destructor
Things like this.
Also, you may need some additional logic to be implemented, when an object is being destructed. Depends on what you're trying to do.
A definition of a destructor should, as far as I know or am concerned, should always look like this:
~msgInfo() { /* free stuff */ }
A constructor on the other hand may look like this:
msgInfo(): m_var1(0), m_var2("Initialize") { /* further initialization */ }
Where what comes between : and { is member variable initialization.
In the destructor you should deallocate anything which was dynamically allocated elsewhere in the class, hence the : notation is no good, since you probably need to do delete on the objects.
In your code you might not have any dynamic memory allocation,so you don't need to provide a destructor.

C++ and destructors (nested classes and general questions)

I am working on an implementation of a binary tree in C++. I am fairly new to the language, and while I understand what structs and destructors are, I am not sure about what happens with nested classes/structs.
In my implementation, I have a nested struct for my binary node. Does this struct need its own destructor, or will all of the nodes be deleted when the destructor for the binary tree itself get called. Does the answer change if I change the struct to a class?
Also, I was told that if you ever call "new" in a class, you need to call "delete" in the destructor. If I initialize an array in my initialization list for a class (i.e. class: array({0})), do I need to delete [] array in my destructor?
Nesting one class (or struct) within another has no effect on the lifetime of the objects. All it does is provide a scope for the class's name, and access to private members in the enclosing class. So your tree nodes won't be automatically destroyed just by virtue of being nested in the tree class.
If you want a tree's nodes to be destroyed when the tree itself is destroyed, you need to ensure that the tree's destructor does that. If you're allocating the nodes manually with new, use delete (or delete[]) in the destructor. Alternatively, you can use something like std::auto_ptr (or std::unique_ptr in C++11), which will do the cleanup in its own destructor so you don't have to write the delete calls yourself.
Changing a struct to a class has no effect on its behavior at runtime. The only difference between a struct and a class in C++ is that a struct's body implicitly begins with public: and a class's body implicitly begins with private:.
it is not necessary for C++ that we have to define destructors in our class/struct.
there is no any changes in destructor if you are going to change struct to class.
but it is good for programming language that if we call memory with new, we have to delete it ourself.
if you are going to define nested class than it is good to make destructor in that class also.
there is no need to use for delete[] for array.

Why can I access private variables in the copy constructor?

I have learned that I can never access a private variable, only with a get-function in the class. But then why can I access it in the copy constructor?
Example:
Field::Field(const Field& f)
{
pFirst = new T[f.capacity()];
pLast = pFirst + (f.pLast - f.pFirst);
pEnd = pFirst + (f.pEnd - f.pFirst);
std::copy(f.pFirst, f.pLast, pFirst);
}
My declaration:
private:
T *pFirst,*pLast,*pEnd;
The access modifiers work on class level, and not on object level.
That is, two objects of the same class can access each others private data.
Why:
Primarily due to efficiency. It would be a non-negligible runtime overhead to check if this == other each time you access other.x which you would have to if the access modifiers worked on object level.
It's also kind of semantically logical if you think of it in terms of scoping: "How big part of the code do I need to keep in mind when modifying a private variable?" – You need to keep the code of the whole class in mind, and this is orthogonal to which objects exist in runtime.
And it's incredibly convenient when writing copy constructors and assignment operators.
IMHO, existing answers do a poor job explaining the "Why" of this - focusing too much on reiterating what behaviour's valid. "access modifiers work on class level, and not on object level." - yes, but why?
The overarching concept here is that it's the programmer(s) designing, writing and maintaining a class who is(are) expected to understand the OO encapsulation desired and empowered to coordinate its implementation. So, if you're writing class X, you're encoding not just how an individual X x object can be used by code with access to it, but also how:
derived classes are able to interact with it (through optionally-pure virtual functions and/or protected access), and
distinct X objects cooperate to provide intended behaviours while honouring the post-conditions and invariants from your design.
It's not just the copy constructor either - a great many operations can involve two or more instances of your class: if you're comparing, adding/multiplying/dividing, copy-constructing, cloning, assigning etc. then it's often the case that you either simply must have access to private and/or protected data in the other object, or want it to allow a simpler, faster or generally better function implementation.
Specifically, these operations may want to take advantage of priviledged access to do things like:
(copy constructors) use a private member of the "rhs" (right hand side) object in an initialiser list, so that a member variable is itself copy-constructed instead of default-constructed (if even legal) then assigned too (again, if legal)
share resources - file handles, shared memory segments, shared_ptrs to reference data etc.
take ownership of things, e.g. auto_ptr<> "moves" ownership to the object under construction
copy private "cache", calibration, or state members needed to construct the new object in an optimally usable state without having to regenerate them from scratch
copy/access diagnostic/trace information kept in the object being copied that's not otherwise accessible through public APIs but might be used by some later exception object or logging (e.g. something about the time/circumstances when the "original" non-copy-constructed instance was constructed)
perform a more efficient copy of some data: e.g. objects may have e.g. an unordered_map member but publicly only expose begin() and end() iterators - with direct access to size() you could reserve capacity for faster copying; worse still if they only expose at() and insert() and otherwise throw....
copy references back to parent/coordination/management objects that might be unknown or write-only for the client code
You can access private members of a class from within the class, even those of another instance.
To understand the answer, I would like to remind you few concepts.
No matter how many objects you create, there is only one copy of one function in memory for that class. It means functions are created only once. However variables are separate for each instance of the class.
this pointer is passed to every function when called.
Now it's because of the this pointer, function is able to locate variables of that particular instance. no matter if it is private of public. it can be accessed inside that function. Now if we pass a pointer to another object of the same class. using this second pointer we will be able to access private members.
Hope this answers your question.
Copy constructor is class' member function and as such has access to class' data members, even those declared as 'private'.
why the man who made that compiler allow this behavior,
that we can see hidden members of an object (that its type is the same of the class where you access the hidden members) in copy constructor or in any method in the class.
The answer: because you when you are in the class that's mean you are the builder or the designer of the class also mean that you know all data members and methods in that class that's why he allow this behavior because you build this class you know every thing about it unlike the users of the class they haven't to know every thing about the class like you.
the idea of hiding data members or method that help the users of this class and not confused them with non important things.
That's it.