1

I am trying to create a vector of 2D points in C++. My question is whether I need to define the copy constructor, the assignment operator and a default constructor for the 2D point before I use the std::vector to store the points? Also, how do I overload operators/ make member functions for the vector that is defined in the std library? Thanks for your help :)

raghav2956
  • 75
  • 8
  • 1
    Most of what you ask depends on how complicated your point structure is. If it's `struct point2d { int x; int y; };` you don't need to do much. What's a `std::rvector`? – user4581301 Dec 21 '18 at 05:59
  • Sorry, I meant std::vector. Yea it is just a simple point structure with 2 fields but I read somewhere (https://cboard.cprogramming.com/cplusplus-programming/36543-how-use-vectors-custom-classes.html) that to use a vector for user-defined types, you need to define those functions? – raghav2956 Dec 21 '18 at 06:02
  • 1
    Probably a better discussion for what I think you are struggling over is found at [What is The Rule of Three?](https://stackoverflow.com/questions/4172722/what-is-the-rule-of-three) – user4581301 Dec 21 '18 at 06:05
  • Possible duplicate of [Conditions for automatic generation of default/copy/move ctor and copy/move assignment operator?](https://stackoverflow.com/questions/4943958/conditions-for-automatic-generation-of-default-copy-move-ctor-and-copy-move-assi) – Nelfeal Dec 21 '18 at 06:07
  • If you want to create an empty vector and then resize it, you might need default constructor – Killzone Kid Dec 21 '18 at 06:07
  • 1
    The TL;DR version of the Rule of Three is if you have a resource you need to manage (dynamic memory that needs deleting, a file that needs to be closed, etc...) then you need (at a minimum) a destructor, a copy constructor, and an assignment operator. Otherwise you want the Rule of Zero: Do nothing. More on this topic: https://en.cppreference.com/w/cpp/language/rule_of_three – user4581301 Dec 21 '18 at 06:08
  • As for how to create an operator overload, that's covered very well at [What are the basic rules and idioms for operator overloading?](https://stackoverflow.com/questions/4421706/what-are-the-basic-rules-and-idioms-for-operator-overloading) – user4581301 Dec 21 '18 at 06:10
  • @user4581301 I'm not sure that's relevant for a 2D point. Presumably, no dynamic allocation is done by his class. – Nelfeal Dec 21 '18 at 06:10
  • @Nelfeal Exactly. If you don't have to do anything, do nothing. Rule of Zero. Code you don't write has no bugs. Still consuming your duplicate pitch. Combined with the link for the rules for operator overloading that might make a good close reason. – user4581301 Dec 21 '18 at 06:12

2 Answers2

3

User-defined types need good copying semantics always. This is true even when you are not putting them into vectors. What it means to copy one object to another varies, but clearly one requirement is that doing so shouldn't crash the program. So the real question is whether your user defined type has good copying semantics or not. Obviously without seeing the type it is hard to say.

If you have a simple type like struct Point { int x, y; }; then that already has good copying semantics and you don't need to do anything more. Same applies if your class contains other objects that themselves have good copying semantics, so there's no problem if you wanted to include a std::string in your type, e.g. struct NamedPoint { std::string name; int x, y; };

Usually the problem arises when the class has to do something in the destructor such as delete some memory. Then you need to write an assignment operator and copy constructor.

Much more detail can be found here.

PS that discussion you linked was somewhat confused.

john
  • 85,011
  • 4
  • 57
  • 81
1

My question is whether I need to define the copy constructor, the assignment operator and a default constructor for the 2D point before I use the std::vector to store the points?

From cppreference:

T must meet the requirements of CopyAssignable and CopyConstructible. (until C++11)

The requirements that are imposed on the elements depend on the actual operations performed on the container. Generally, it is required that element type is a complete type and meets the requirements of Erasable, but many member functions impose stricter requirements. (since C++11) (until C++17)

The requirements that are imposed on the elements depend on the actual operations performed on the container. Generally, it is required that element type meets the requirements of Erasable, but many member functions impose stricter requirements. This container (but not its members) can be instantiated with an incomplete element type if the allocator satisfies the allocator completeness requirements. (since C++17)

Generally, yes, you want a copy constructor, an assignment operator and a default constructor. But these can be implicitly provided, meaning they will be generated by the compiler. Look at this question to know what exactly is implicitly defined in what situation.

Also, how do I overload operators/ make member functions for the vector that is defined in the std library?

You don't. The standard library is not to be modified; at best, you can add some code to the std namespace under certain circumstances, but this is not one of them.

Community
  • 1
  • 1
Nelfeal
  • 12,593
  • 1
  • 20
  • 39
  • Isn't extending the `std` namespace actually an undefined behavior? – user3366592 Dec 21 '18 at 06:31
  • @user3366592 Generally, yes. There actually is a page on cppreference dedicated to that: [Extending the namespace `std`](https://en.cppreference.com/w/cpp/language/extending_std). – Nelfeal Dec 21 '18 at 06:39
  • Unless specified explicitly, it's undefined behavior that most likely works until you update your compiler/stl. Best to define the operators in class (`=default` if correct) or in the namespace of the class (ADL lookup), not sure if the last is allowed for assign. – JVApen Dec 21 '18 at 07:49