Several default member functions of classes in C++

Several default member functions of classes in C++

1. Constructor

The constructor is a special member function. The name is the same as the class name. It is automatically called by the compiler when creating a class type object to ensure that each data member has an appropriate initial value and is stored in the object. Only called once during the entire life cycle.

The main task of the constructor is not to open space to create objects, but to initialize objects.

  1. ConstructorThe function name is the same as the class name.

  2. Constructorhas no return value.

  3. When a class instantiates an object the compiler will automatically call the constructor to initialize the object.

  4. Constructorscan be overloaded.

  5. The parameterless constructor and the all-default constructor are both called default constructors, and there can only be one default constructor, or there may not be. Note: Constructors without parameters, full default constructors, and constructors generated by default by the compiler if we have not written them can all be considered default constructors. In other words, the constructor and the default constructor are different! ! !

  6. If there is no explicitly defined constructor in the class, the C++ compiler will automatically generate a parameterless default constructor. Once the user explicitly defines it, the compiler will no longer generate it. The default-generated constructor does not process built-in types, and its default constructor will be called for custom types.

To put it simply: the default constructor is which can initialize the object without passing parameters.

If a class does not have a default constructor, or it writes its own constructor, but the constructor is neither a parameterless constructor nor a fully default constructor, then the class will be instantiated when it is instantiated. Corresponding parameters must be passed! ! Otherwise, an error will be reported. (It is recommended that there be a default constructor in the class)

2. Destructor

Cleaning up the resources in the object is not the destruction of the object itself, but the cleaning up of the resources in the object, such as the release of heap space. ==The destructor will be automatically called when the object is destroyed.

  1. Destructor name: ~class name
  2. The destructorhas no parameters and no return value.
  3. There can only be one destructor in a class and it cannot be overloaded. If the definition is not displayed, the system will automatically generate a default destructor.
  4. The destructor automatically generated by the system does not process built-in types, and its destructor will be called for custom types.
  5. If the class does not apply for dynamic resources (such as heap space), the destructor does not need to be written. You can directly use the default destructor generated by the compiler. However, when applying for dynamic resources in the class, you must explicitly declare it yourself. Write a destructor to release resources, otherwise it will cause memory leaks! !
  6. At the end of the object’s life cycle, the system will automatically call the destructor to clean up the resources in the object.

The destruction order of multiple objects in the same scope: last in, first out! The last constructed object is destroyed first. (stack frame)

3. Copy construction (C++ stipulates that copying between objects must call the copy constructor)

Copy constructor: There is only a single formal parameter. This formal parameter is a reference to an object of this class type (usually modified with const). It is automatically called by the compiler when creating a new object using an existing class type object.

  1. The copy constructor is essentially an overload of theconstructor.
  2. The parameter of the copy constructor has one and only one and must be a reference to a class type object, and it is recommended to modify it with const. Using the pass-by-value method will report an error during the compilation phase because it will cause infinite recursive calls.
  3. If not explicitly defined, the compiler will automatically generate a default copy constructor. The default copy constructor copies built-in types** in byte order according to memory storage (memcopy). This type of copy is called shallow copy, or value copy. **Call its copy constructor on a custom type.

Why the parameters of the copy constructor must be references of class type objects: Because if you use pass-by-value parameters, you must copy the actual parameters to the formal parameters when passing parameters. , and the == copy constructor parameter type is the class type itself. When copying, the copy constructor of the class must be called! ! ! ==When calling the copy constructor, you need to pass parameters, and when you pass the parameters, you need to call the copy constructor…so it will cause infinite recursive calls! This problem can be avoided by using reference passing parameters.

Deep and shallow copy issues:

==When class member variables dynamically open space on the heap to store values, the copy constructor must be a deep copy written by yourself! ! ==The default copy constructor generated by the compiler will not work! There will be a memory problem-The member variables in the two objects point to the same heap space! !

  1. Changes made to one of the objects will affect the other.
  2. When both objects are destroyed, the destructor will be called and the same space will be released twice. An error will be reported! !

4. Assignment overloading

1. Operator overloading

C++ introduces operator overloading functions in order to enhance the readability of the code. The operator overloading function is a function with a special function name. The purpose is to enable custom types to use various operators normally!

This overloading has nothing to do with function overloading! ! What this means here is that redefines the meaning of each operator for different custom types!

After the operator is overloaded, the class type can use the operator normally! The compiler will automatically parse it into the corresponding function call!

//The number of parameters is determined by the operand
// Function prototype: return value type operator (parameter list)
bool operator==(const Date & d1, const Date & d2)
{
  // Redefine the meaning of the == operator for the Date type! ! easy to use
  // ...
}

int main()
{
  Date d1;
  Date d2;
  //Write it like this directly when using it! The compiler will parse it into a function call: operator==(d1, d2)
  if(d1 == d2)
  {
    // ...
  }
}
  1. operator can only be followed by operators.
  2. Operator overloading functions must have parameters of class type (redefining the meaning of each operator for different custom types).
  3. The operator overloaded function can be a global function or a member function within the class (more recommended).
  4. When an operator overloaded function is overloaded as a member function in a class, its formal parameters appear to be 1 less than the number of operands, because the first parameter of the member function is a hidden this pointer.
  5. There are 5 operators that cannot be overloaded: . .* :: sizeof ?: (sizeof is an operator!)
2. Assignment operator overloading

is a special operator overload, which is the assignment operator!

//Parameters: const T & amp; references reduce the cost of passing values and are decorated with const
//Return value: There is a return value to support continuous assignment! T & returns a reference to reduce consumption,
class Date
{
public:
  // ...
  Date & operator=(const Date & d)
  {
    // Check whether you assigned a value to yourself! Improve efficiency 
    if(this != & amp;d)
    {
      year_ = d.year_;
      month_ = d.month_;
      day_ = d.day_;
    }
    // There is a return value to support continuous assignment!
    return *this; // this is a pointer to the object, just like i=j will return i
  }
private:
  int year_;
  int month_;
  int day_;
};
  1. When the user does not explicitly implement assignment overloading, the compiler will generate a default assignment operator overload function, which copies the built-in type in byte order (memcopy) when stored in memory, that is, shallow copy.
  2. The == assignment operator can only be overloaded into class member functions and cannot be overloaded into global functions. == Because if the assignment operator is not implemented explicitly, the compiler will generate a default one. At this time, if the user implements a global assignment operator overload outside the class, will it conflict with the default assignment operator overload generated by the compiler in the class? ? ? (But other operator overloads can be implemented both within the class and globally, and the compiler will call the ones within the class first! Guess: It should be that the operator overloads within the class will be compiled into inline functions, so they will not conflict with the global ones. ! Not quite!) It’s always weird here! ! ! Just treat it as a feature. Assignment overloading is a special member function and cannot be treated with common sense.

Assignment overloading is to assign the value of an object to another object that already exists! The copy constructor is called when instantiates a new object! !

class Date
{
  // ...
};
int main()
{
  Date d1;
  // What is called here is copy construction! Initialize a new object!
  Date d2 = d1; // => Date d2(d1);
  Date d3;
  // This call is assignment overloading! Assign the value of one object to another existing object
  d3 = d1;
  return 0
}

**Assignment operator overloading also has deep and shallow copy problems: **Similar to copy construction, when class member variables dynamically open up space on the heap to store values, the assignment overloaded function generated by the compiler by default will cause members in multiple objects The variables point to the same heap space! !

  1. Changes made to one of the objects will affect the other.
  2. When both objects are destroyed, the destructor will be called and the same space will be released twice. An error will be reported! !

At this time, you need to write the assignment overload yourself to perform a deep copy!

5. Ordinary object address overloading

Generally, you can use the default generated one.

class Date
{
public:
  Date* operator &()
  {
  return this;
  }
private :
  int _year;
  int _month;
  int _day;
};

6. constObject address overloading

Generally, you can use the default generated one.

class Date
{
public:
  const Date* operator & amp;() const
  {
  return this;
  }
private :
  int _year;
  int _month;
  int _day;
};

Here is a link at the end. Welcome to learn and make progress together! https://xxetb.xet.tech/s/4G6TWG