User-defined types, such as strings, date, complex, consortium, and files often overload binary operators to achieve access, additional or merge mechanisms. But to properly implement operators will bring a certain challenge to design, implementation, and performance. This article summarizes how to select the correct policy to overload this operator for the user-defined type. Consider the following expression: int x = 4 2;
Built-in operators have two types of operands, add and return right value 6, and then assigned to X. We can determine the built-in is a binary, symmetrical, can be exchangeable. The type of result is the same as its operand type. According to this rule, when you define a type overload operator for a user, you should follow the characteristics of the corresponding internal operator.
Define type overload operators for users is a common programming task. Although C provides several implementation methods, they easily produce misunderstandings, this misunderstanding often affects the correctness, performance of the code, and compatibility with standard library components. Let's analyze the characteristics of the internal operator and try to imitate its corresponding overload mechanism.
Step 1: Select between member functions and non-member functions
You can implement binary operators such as , - and ==, for example:
Class string {public: BOOL Operator == (const string & s); // Compare * this and s};
This method is problematic. Relative to its built-in operator, the overloaded operator does not have symmetry here; its two parameters are: const string * const (this parameter is implicit), and the other is: CONST STRING &. Therefore, some STL algorithms and containers will not properly handle such objects.
Another alternative method is to define the overload operator as an external (extern) function, which is the same parameter as two types:
String Operator (Const String & S1, Const String S2);
In this way, class string must declare the overload operator as a friend:
Class string {public: Friend String Operator (Const String & S1, Const String & S2);
Step 2: Two difficulties for return values
As mentioned earlier, the built-in operator returns the right value, the type is the same as the number of operands. But especially if you return an object efficiency in the caller stack, especially when processing large objects. So can you return a pointer or a reference? The answer is not. Because the return pointer destroy parameter type and the return value type should be the same rule. Worse, link multiple expressions will become impossible:
String S1, S2, S3; STRING RES; RES = S1 S2 S3; // It is not possible to use string * as return value
Although there is an approach to define an additional operator overload version, this method is that we don't want to use because the returned pointer must point to the dynamically assigned object. In this case, if the pointer returned by the caller release fails, the memory leak will result. Obviously, returning String * is not a good idea.