Nice video. Very good explanation without unnecessary details. One thing I would mention (without going into too much detail) is the Rule of 5, which states that if any of the following 5 member functions is explicitly defined then all of them should be explicitly defined: - destructor - copy constructor - copy assignment operator - move constructor - move assignment operator Also, it is a good idea to always provide a default constructor to your custom classes unless you have a really good reason not to.
Thanks for the comment! The video about the rule of 5 or all or nothing is coming soon 😬 I tried to keep it short and sweet without giving any wrong advice here. I would not agree that we should provide a default constructor at all times. Could you elaborate why?
@@CodeForYourself OK, just to clarify, the best thing to do is to provide no constructors, in which case you get a free default constructor. But if you define at least one constructor then it is a good idea to also provide a default constructor and the reason is that some of the operations in STL require the type to be default constructible. For example, if you have a vector of some type and you want to resize it then the type must be default constructible. Basically, all the places where you want to create an object but you don't want to give it a meaningful value (because the value will be given at some later point) you will need to default-construct it. Also, if a class has a member which is not default constructible then the whole class doesn't get a "free" default constructor. Finally, I'm a big proponent of value semantics and one of the requirements for value semantics is that the object must be default constructible. If you take a look in the STL you'll see that almost all of the classes are default constructible and most of them support value semantics (although, there are a few classes which are intentionally designed to use reference semantics instead).
I would not say that I agree here. Some types make no sense when in undefined state. I would say it is a good idea to create classes from the concrete data they will operate on, ideally so that they would remain constant for the duration of their existence 🤔 A default constructor makes sense only in very limited settings if you ask me. As for STL, I can totally resize the vector without the default constructor by just providing the value that has to be copied into the newly constructed values. Or I could just use emplace_back and such. Most of the algorithms also do not require objects being default constructible as far as I know 🤔 Am I missing the point?
@@CodeForYourself You're totally right. You can resize a vector without relying on the default constructor. My point was that most of the classes in STL have a default constructor even if it doesn't make much sense. For example, std::unique_ptr. It is used to safely manage a resource. But it has a default constructor which doesn't hold anything, which makes it quite unsafe especially if you assume that it holds a value without checking first. Even classes which are purely based on reference semantics have default constructors, like std::span and std::string_view. Why would one need to create an empty span or an empty string_view? I don't know but it is defined in the standard. All I'm trying to say is that if you want your classes to be as universally usable as the classes in STL then you should follow the same principles used to define the STL, like: have a default constructor, follow the rule of 5, support copy and move operations, use RAII, etc., etc. I guess, I'm thinking from the perspective of writing libraries. These rules are good to follow if you're writing classes that will be used by many programmers in different situations. If you're writing a class which only you (or the people in your project) will use, then feel free to define whatever rules you want as long as they are well documented and are easy to follow.
Yeah, you totally have a point from a generic perspective. At the same time, I feel it does come down to design decisions. Like a unique pointer had to follow the semantics of a raw pointer, i.e., should be nullable as we might want to have a pointer that owns no data, an empty span has a semantic meaning too, right? There are also other classes that make no sense being default constructible. So I guess the point I would like to make is that it mostly comes down to what we're trying to model with a particular class and what it is that we want to represent. At least that's the way I tend to think about it all.
Thanks for watching as always! Please leave a comment with any suggestions or ideas or feedback that you might have! 🙏
Nice video. Very good explanation without unnecessary details.
One thing I would mention (without going into too much detail) is the Rule of 5, which states that if any of the following 5 member functions is explicitly defined then all of them should be explicitly defined:
- destructor
- copy constructor
- copy assignment operator
- move constructor
- move assignment operator
Also, it is a good idea to always provide a default constructor to your custom classes unless you have a really good reason not to.
Thanks for the comment!
The video about the rule of 5 or all or nothing is coming soon 😬 I tried to keep it short and sweet without giving any wrong advice here.
I would not agree that we should provide a default constructor at all times. Could you elaborate why?
@@CodeForYourself OK, just to clarify, the best thing to do is to provide no constructors, in which case you get a free default constructor. But if you define at least one constructor then it is a good idea to also provide a default constructor and the reason is that some of the operations in STL require the type to be default constructible.
For example, if you have a vector of some type and you want to resize it then the type must be default constructible. Basically, all the places where you want to create an object but you don't want to give it a meaningful value (because the value will be given at some later point) you will need to default-construct it.
Also, if a class has a member which is not default constructible then the whole class doesn't get a "free" default constructor.
Finally, I'm a big proponent of value semantics and one of the requirements for value semantics is that the object must be default constructible. If you take a look in the STL you'll see that almost all of the classes are default constructible and most of them support value semantics (although, there are a few classes which are intentionally designed to use reference semantics instead).
I would not say that I agree here. Some types make no sense when in undefined state. I would say it is a good idea to create classes from the concrete data they will operate on, ideally so that they would remain constant for the duration of their existence 🤔 A default constructor makes sense only in very limited settings if you ask me.
As for STL, I can totally resize the vector without the default constructor by just providing the value that has to be copied into the newly constructed values. Or I could just use emplace_back and such. Most of the algorithms also do not require objects being default constructible as far as I know 🤔 Am I missing the point?
@@CodeForYourself You're totally right. You can resize a vector without relying on the default constructor. My point was that most of the classes in STL have a default constructor even if it doesn't make much sense.
For example, std::unique_ptr. It is used to safely manage a resource. But it has a default constructor which doesn't hold anything, which makes it quite unsafe especially if you assume that it holds a value without checking first.
Even classes which are purely based on reference semantics have default constructors, like std::span and std::string_view. Why would one need to create an empty span or an empty string_view? I don't know but it is defined in the standard.
All I'm trying to say is that if you want your classes to be as universally usable as the classes in STL then you should follow the same principles used to define the STL, like: have a default constructor, follow the rule of 5, support copy and move operations, use RAII, etc., etc.
I guess, I'm thinking from the perspective of writing libraries. These rules are good to follow if you're writing classes that will be used by many programmers in different situations. If you're writing a class which only you (or the people in your project) will use, then feel free to define whatever rules you want as long as they are well documented and are easy to follow.
Yeah, you totally have a point from a generic perspective. At the same time, I feel it does come down to design decisions. Like a unique pointer had to follow the semantics of a raw pointer, i.e., should be nullable as we might want to have a pointer that owns no data, an empty span has a semantic meaning too, right? There are also other classes that make no sense being default constructible. So I guess the point I would like to make is that it mostly comes down to what we're trying to model with a particular class and what it is that we want to represent. At least that's the way I tend to think about it all.
this video is very important. concise and well explained. thanks!
Thanks for the kind words!
sure, another great video!
Really great videos. Keep them up!
Glad you like them!