Learn C++

21.12 — Overloading the assignment operator

The copy assignment operator (operator=) is used to copy values from one object to another already existing object .

Related content

As of C++11, C++ also supports “Move assignment”. We discuss move assignment in lesson 22.3 -- Move constructors and move assignment .

Copy assignment vs Copy constructor

The purpose of the copy constructor and the copy assignment operator are almost equivalent -- both copy one object to another. However, the copy constructor initializes new objects, whereas the assignment operator replaces the contents of existing objects.

The difference between the copy constructor and the copy assignment operator causes a lot of confusion for new programmers, but it’s really not all that difficult. Summarizing:

  • If a new object has to be created before the copying can occur, the copy constructor is used (note: this includes passing or returning objects by value).
  • If a new object does not have to be created before the copying can occur, the assignment operator is used.

Overloading the assignment operator

Overloading the copy assignment operator (operator=) is fairly straightforward, with one specific caveat that we’ll get to. The copy assignment operator must be overloaded as a member function.

This prints:

This should all be pretty straightforward by now. Our overloaded operator= returns *this, so that we can chain multiple assignments together:

Issues due to self-assignment

Here’s where things start to get a little more interesting. C++ allows self-assignment:

This will call f1.operator=(f1), and under the simplistic implementation above, all of the members will be assigned to themselves. In this particular example, the self-assignment causes each member to be assigned to itself, which has no overall impact, other than wasting time. In most cases, a self-assignment doesn’t need to do anything at all!

However, in cases where an assignment operator needs to dynamically assign memory, self-assignment can actually be dangerous:

First, run the program as it is. You’ll see that the program prints “Alex” as it should.

Now run the following program:

You’ll probably get garbage output. What happened?

Consider what happens in the overloaded operator= when the implicit object AND the passed in parameter (str) are both variable alex. In this case, m_data is the same as str.m_data. The first thing that happens is that the function checks to see if the implicit object already has a string. If so, it needs to delete it, so we don’t end up with a memory leak. In this case, m_data is allocated, so the function deletes m_data. But because str is the same as *this, the string that we wanted to copy has been deleted and m_data (and str.m_data) are dangling.

Later on, we allocate new memory to m_data (and str.m_data). So when we subsequently copy the data from str.m_data into m_data, we’re copying garbage, because str.m_data was never initialized.

Detecting and handling self-assignment

Fortunately, we can detect when self-assignment occurs. Here’s an updated implementation of our overloaded operator= for the MyString class:

By checking if the address of our implicit object is the same as the address of the object being passed in as a parameter, we can have our assignment operator just return immediately without doing any other work.

Because this is just a pointer comparison, it should be fast, and does not require operator== to be overloaded.

When not to handle self-assignment

Typically the self-assignment check is skipped for copy constructors. Because the object being copy constructed is newly created, the only case where the newly created object can be equal to the object being copied is when you try to initialize a newly defined object with itself:

In such cases, your compiler should warn you that c is an uninitialized variable.

Second, the self-assignment check may be omitted in classes that can naturally handle self-assignment. Consider this Fraction class assignment operator that has a self-assignment guard:

If the self-assignment guard did not exist, this function would still operate correctly during a self-assignment (because all of the operations done by the function can handle self-assignment properly).

Because self-assignment is a rare event, some prominent C++ gurus recommend omitting the self-assignment guard even in classes that would benefit from it. We do not recommend this, as we believe it’s a better practice to code defensively and then selectively optimize later.

The copy and swap idiom

A better way to handle self-assignment issues is via what’s called the copy and swap idiom. There’s a great writeup of how this idiom works on Stack Overflow .

The implicit copy assignment operator

Unlike other operators, the compiler will provide an implicit public copy assignment operator for your class if you do not provide a user-defined one. This assignment operator does memberwise assignment (which is essentially the same as the memberwise initialization that default copy constructors do).

Just like other constructors and operators, you can prevent assignments from being made by making your copy assignment operator private or using the delete keyword:

Note that if your class has const members, the compiler will instead define the implicit operator= as deleted. This is because const members can’t be assigned, so the compiler will assume your class should not be assignable.

If you want a class with const members to be assignable (for all members that aren’t const), you will need to explicitly overload operator= and manually assign each non-const member.

guest

This browser is no longer supported.

Upgrade to Microsoft Edge to take advantage of the latest features, security updates, and technical support.

Operator overloading

  • 8 contributors

The operator keyword declares a function specifying what operator-symbol means when applied to instances of a class. This gives the operator more than one meaning, or "overloads" it. The compiler distinguishes between the different meanings of an operator by examining the types of its operands.

type operator operator-symbol ( parameter-list )

You can redefine the function of most built-in operators globally or on a class-by-class basis. Overloaded operators are implemented as functions.

The name of an overloaded operator is operator x , where x is the operator as it appears in the following table. For example, to overload the addition operator, you define a function called operator+ . Similarly, to overload the addition/assignment operator, += , define a function called operator+= .

Redefinable Operators

1 Two versions of the unary increment and decrement operators exist: preincrement and postincrement.

See General Rules for Operator Overloading for more information. The constraints on the various categories of overloaded operators are described in the following topics:

Unary Operators

Binary Operators

Function Call

Subscripting

Class-Member Access

Increment and Decrement .

User-Defined Type Conversions

The operators shown in the following table cannot be overloaded. The table includes the preprocessor symbols # and ## .

Nonredefinable Operators

Although overloaded operators are usually called implicitly by the compiler when they are encountered in code, they can be invoked explicitly the same way as any member or nonmember function is called:

The following example overloads the + operator to add two complex numbers and returns the result.

In this section

General Rules for Operator Overloading

Overloading Unary Operators

Member Access

C++ Built-in Operators, Precedence and Associativity Keywords

Was this page helpful?

Coming soon: Throughout 2024 we will be phasing out GitHub Issues as the feedback mechanism for content and replacing it with a new feedback system. For more information see: https://aka.ms/ContentUserFeedback .

Submit and view feedback for

Additional resources

operator overloading

Customizes the C++ operators for operands of user-defined types.

Overloaded operators are functions with special function names:

Overloaded operators

When an operator appears in an expression , and at least one of its operands has a class type or an enumeration type , then overload resolution is used to determine the user-defined function to be called among all the functions whose signatures match the following:

Note: for overloading user-defined conversion functions , user-defined literals , allocation and deallocation see their respective articles.

Overloaded operators (but not the built-in operators) can be called using function notation:

Restrictions

  • The operators :: (scope resolution), . (member access), .* (member access through pointer to member), and ?: (ternary conditional) cannot be overloaded.
  • New operators such as ** , <> , or &| cannot be created.
  • The overloads of operators && and || lose short-circuit evaluation.
  • The overload of operator -> must either return a raw pointer, or return an object (by reference or by value) for which operator -> is in turn overloaded.
  • It is not possible to change the precedence, grouping, or number of operands of operators.

Canonical implementations

Other than the restrictions above, the language puts no other constraints on what the overloaded operators do, or on the return type (it does not participate in overload resolution), but in general, overloaded operators are expected to behave as similar as possible to the built-in operators: operator + is expected to add, rather than multiply its arguments, operator = is expected to assign, etc. The related operators are expected to behave similarly ( operator + and operator + = do the same addition-like operation). The return types are limited by the expressions in which the operator is expected to be used: for example, assignment operators return by reference to make it possible to write a = b = c = d , because the built-in operators allow that.

Commonly overloaded operators have the following typical, canonical forms: [1]

Assignment operator

The assignment operator ( operator = ) has special properties: see copy assignment and move assignment for details.

The canonical copy-assignment operator is expected to perform no action on self-assignment , and to return the lhs by reference:

The canonical move assignment is expected to leave the moved-from object in valid state (that is, a state with class invariants intact), and either do nothing or at least leave the object in a valid state on self-assignment, and return the lhs by reference to non-const, and be noexcept:

In those situations where copy assignment cannot benefit from resource reuse (it does not manage a heap-allocated array and does not have a (possibly transitive) member that does, such as a member std::vector or std::string ), there is a popular convenient shorthand: the copy-and-swap assignment operator, which takes its parameter by value (thus working as both copy- and move-assignment depending on the value category of the argument), swaps with the parameter, and lets the destructor clean it up.

This form automatically provides strong exception guarantee , but prohibits resource reuse.

Stream extraction and insertion

The overloads of operator>> and operator<< that take a std:: istream & or std:: ostream & as the left hand argument are known as insertion and extraction operators. Since they take the user-defined type as the right argument ( b in a@b ), they must be implemented as non-members.

These operators are sometimes implemented as friend functions .

Function call operator

When a user-defined class overloads the function call operator, operator ( ) , it becomes a FunctionObject type. Many standard algorithms, from std:: sort to std:: accumulate accept objects of such types to customize behavior. There are no particularly notable canonical forms of operator ( ) , but to illustrate the usage

Increment and decrement

When the postfix increment and decrement appear in an expression, the corresponding user-defined function ( operator ++ or operator -- ) is called with an integer argument 0 . Typically, it is implemented as T operator ++ ( int ) , where the argument is ignored. The postfix increment and decrement operator is usually implemented in terms of the prefix version:

Although canonical form of pre-increment/pre-decrement returns a reference, as with any operator overload, the return type is user-defined; for example the overloads of these operators for std::atomic return by value.

Binary arithmetic operators

Binary operators are typically implemented as non-members to maintain symmetry (for example, when adding a complex number and an integer, if operator+ is a member function of the complex type, then only complex + integer would compile, and not integer + complex ). Since for every binary arithmetic operator there exists a corresponding compound assignment operator, canonical forms of binary operators are implemented in terms of their compound assignments:

Relational operators

Standard algorithms such as std:: sort and containers such as std:: set expect operator < to be defined, by default, for the user-provided types, and expect it to implement strict weak ordering (thus satisfying the Compare requirements). An idiomatic way to implement strict weak ordering for a structure is to use lexicographical comparison provided by std::tie :

Typically, once operator < is provided, the other relational operators are implemented in terms of operator < .

Likewise, the inequality operator is typically implemented in terms of operator == :

When three-way comparison (such as std::memcmp or std::string::compare ) is provided, all six relational operators may be expressed through that:

Array subscript operator

User-defined classes that provide array-like access that allows both reading and writing typically define two overloads for operator [ ] : const and non-const variants:

If the value type is known to be a built-in type, the const variant should return by value.

Where direct access to the elements of the container is not wanted or not possible or distinguishing between lvalue c [ i ] = v ; and rvalue v = c [ i ] ; usage, operator[] may return a proxy. see for example std::bitset::operator[] .

To provide multidimensional array access semantics, e.g. to implement a 3D array access a [ i ] [ j ] [ k ] = x ; , operator[] has to return a reference to a 2D plane, which has to have its own operator[] which returns a reference to a 1D row, which has to have operator[] which returns a reference to the element. To avoid this complexity, some libraries opt for overloading operator ( ) instead, so that 3D access expressions have the Fortran-like syntax a ( i, j, k ) = x ;

Bitwise arithmetic operators

User-defined classes and enumerations that implement the requirements of BitmaskType are required to overload the bitwise arithmetic operators operator & , operator | , operator ^ , operator~ , operator & = , operator | = , and operator ^ = , and may optionally overload the shift operators operator << operator >> , operator >>= , and operator <<= . The canonical implementations usually follow the pattern for binary arithmetic operators described above.

Boolean negation operator

The operator operator ! is commonly overloaded by the user-defined classes that are intended to be used in boolean contexts. Such classes also provide a user-defined conversion function explicit operator bool ( ) (see std::basic_ios for the standard library example), and the expected behavior of operator ! is to return the value opposite of operator bool .

Rarely overloaded operators

The following operators are rarely overloaded:

  • The address-of operator, operator & . If the unary & is applied to an lvalue of incomplete type and the complete type declares an overloaded operator & , the behavior is undefined (until C++11) it is unspecified whether the operator has the built-in meaning or the operator function is called (since C++11) . Because this operator may be overloaded, generic libraries use std::addressof to obtain addresses of objects of user-defined types. The best known example of a canonical overloaded operator& is the Microsoft class CComPtr . An example of its use in EDSL can be found in boost.spirit .
  • The boolean logic operators, operator && and operator || . Unlike the built-in versions, the overloads cannot implement short-circuit evaluation. Also unlike the built-in versions, they do not sequence their left operand before the right one. (until C++17) In the standard library, these operators are only overloaded for std::valarray .
  • The comma operator, operator, . Unlike the built-in version, the overloads do not sequence their left operand before the right one. (until C++17) Because this operator may be overloaded, generic libraries use expressions such as a, void ( ) ,b instead of a,b to sequence execution of expressions of user-defined types. The boost library uses operator, in boost.assign , boost.spirit , and other libraries. The database access library SOCI also overloads operator, .
  • The member access through pointer to member operator - > * . There are no specific downsides to overloading this operator, but it is rarely used in practice. It was suggested that it could be part of smart pointer interface , and in fact is used in that capacity by actors in boost.phoenix . It is more common in EDSLs such as cpp.react .

Defect reports

The following behavior-changing defect reports were applied retroactively to previously published C++ standards.

  • Operator precedence
  • Alternative operator syntax
  • ↑ Operator Overloading on StackOverflow C++ FAQ

Code With C

The Way to Programming

  • C Tutorials
  • Java Tutorials
  • Python Tutorials
  • PHP Tutorials
  • Java Projects

Mastering Operator Overloads: A Comprehensive Guide

CodeLikeAGirl

Hey there, tech-savvy pals! Today, I’m diving headfirst into the fabulous world of operator overloads! 🚀 As an code-savvy friend 😋 with killer coding chops, I know the buzz around mastering these bad boys is real. So buckle up, grab your chai ☕, and let’s unravel the magic of operator overloads together!

Understanding Operator Overloads

Definition of operator overloads.

Operator overloading, my fellow code enthusiasts, is a fancy way of giving superpowers to those operators (+, -, *, /) in programming languages . It’s like teaching an old dog new tricks! 🐕✨

Importance of Operator Overloads in Programming

Why bother with operator overloads , you ask? Well, they make your code elegant, efficient, and oh-so-fancy! Imagine customizing how your objects behave with just a simple operator. It’s like painting with a broad brush! 🎨

Overloading Unary Operators

Explanation of unary operators.

Unary operators, folks, work on a single operand. Think of them as the solo artists of the programming world, strutting their stuff like Beyoncé on stage! 💃🎤

Examples of Overloading Unary Operators

Picture this: overloading the ++ operator to increment a value or the ~ operator to complement a binary number . It’s like jazzing up your code with some killer solos! 🎸🎶

Overloading Binary Operators

Explanation of binary operators.

Now, binary operators are the dynamic duos of the coding universe, working their magic on two operands like peanut butter and jelly! 🥪✨

Examples of Overloading Binary Operators

From overloading the + operator to concatenate strings to using the == operator to compare custom objects, the possibilities are endless! It’s like salsa dancing with your code! 💃💻

Best Practices for Operator Overloads

Avoiding ambiguity in operator overloads.

Ah, the dreaded ambiguity! To steer clear of the confusion, make sure your operator overloads have clear semantics and don’t leave room for misinterpretation. It’s like speaking fluently in code! 💬💻

Choosing the Right Operator Overload for Different Data Types

Different data types , different strokes! Be mindful of choosing the right operator overload to ensure smooth sailing across various data types . It’s like matching the right shoes with your outfit!👠👗

Common Challenges in Operator Overloads

Handling error cases in operator overloads.

Errors? Ain’t nobody got time for that! Make sure to handle those pesky error cases gracefully in your operator overloads. It’s like being the calm in the coding storm! 🌪️💻

Ensuring Consistency in Operator Overloads

Consistency is key, my pals! Keep your operator overloads consistent across your codebase for that smooth coding experience. It’s like creating a symphony of code! 🎶💻

Overall, mastering operator overloads is like adding spices to your favorite dish – it brings out the flavor and makes it oh-so-delicious! Remember, with great power comes great responsibility, so wield those operator overloads wisely, my coding comrades! 💻✨

Stay techy, stay sassy! Adios, amigos! ✌️🚀

Program Code – Mastering Operator Overloads: A Comprehensive Guide

Code output:.

The output of the given code snippet, when run, will be:

Code Explanation:

The program defines a class ComplexNumber to represent complex numbers and provide operator overloads for common mathematical operations.

  • The __init__ method initializes each complex number with a real and an imaginary component.
  • The __repr__ method allows us to print complex number objects in a way that’s human-readable, showing the real and imaginary parts.
  • The __add__ method enables the use of the + operator to add two complex numbers, resulting in a new complex number whose real and imaginary parts are the sums of the real and imaginary parts of the operands, respectively.
  • The __sub__ method allows the use of the - operator to subtract one complex number from another, yielding the differences in real and imaginary parts.
  • __mul__ describes how two complex numbers are multiplied by employing the * operator, using the standard formula for complex multiplication.
  • __truediv__ enables division with the / operator. It uses the conjugate to divide complex numbers, following standard rules for complex division.
  • The __eq__ method defines how two complex numbers are compared for equality using == . It returns True if both the real and imaginary parts are equal, otherwise False.
  • The __ne__ method defines inequality check ( != ) and it yields True if the complex numbers are not equal.

The code then creates two complex number instances, a and b , and performs addition , subtraction, multiplication, division, and equality checks, displaying the results. Each mathematical operation utilizes the overloaded operator corresponding to it, demonstrating the power and flexibility of operator overloading in Python.

You Might Also Like

Revolutionary feedback control project for social networking: enhancing information spread, the evolution of web development: past, present, and future, defining the future: an overview of software services, exploring the layers: the multifaceted world of software, deep dive: understanding the ‘case when’ clause in sql.

Avatar photo

Leave a Reply Cancel reply

Your email address will not be published. Required fields are marked *

Latest Posts

codewithc 61 Cutting-Edge Artificial Intelligence Project Unveiled in Machine Learning World

Cutting-Edge Artificial Intelligence Project Unveiled in Machine Learning World

75 Enhancing Exams with Image Processing: E-Assessment Project

Enhancing Exams with Image Processing: E-Assessment Project

73 Cutting-Edge Blockchain Projects for Cryptocurrency Enthusiasts - Project

Cutting-Edge Blockchain Projects for Cryptocurrency Enthusiasts – Project

67 Artificial Intelligence Marvel: Cutting-Edge Machine Learning Project

Artificial Intelligence Marvel: Cutting-Edge Machine Learning Project

84 Personalized Affective Feedback Project: Deep Learning Solutions for Student Frustration in IT

Personalized Affective Feedback Project: Deep Learning Solutions for Student Frustration in IT

Privacy overview.

en_US

Sign in to your account

Username or Email Address

Remember Me

cppreference.com

Copy assignment operator.

A copy assignment operator is a non-template non-static member function with the name operator = that can be called with an argument of the same class type and copies the content of the argument without mutating the argument.

[ edit ] Syntax

For the formal copy assignment operator syntax, see function declaration . The syntax list below only demonstrates a subset of all valid copy assignment operator syntaxes.

[ edit ] Explanation

The copy assignment operator is called whenever selected by overload resolution , e.g. when an object appears on the left side of an assignment expression.

[ edit ] Implicitly-declared copy assignment operator

If no user-defined copy assignment operators are provided for a class type, the compiler will always declare one as an inline public member of the class. This implicitly-declared copy assignment operator has the form T & T :: operator = ( const T & ) if all of the following is true:

  • each direct base B of T has a copy assignment operator whose parameters are B or const B & or const volatile B & ;
  • each non-static data member M of T of class type or array of class type has a copy assignment operator whose parameters are M or const M & or const volatile M & .

Otherwise the implicitly-declared copy assignment operator is declared as T & T :: operator = ( T & ) .

Due to these rules, the implicitly-declared copy assignment operator cannot bind to a volatile lvalue argument.

A class can have multiple copy assignment operators, e.g. both T & T :: operator = ( T & ) and T & T :: operator = ( T ) . If some user-defined copy assignment operators are present, the user may still force the generation of the implicitly declared copy assignment operator with the keyword default . (since C++11)

The implicitly-declared (or defaulted on its first declaration) copy assignment operator has an exception specification as described in dynamic exception specification (until C++17) noexcept specification (since C++17)

Because the copy assignment operator is always declared for any class, the base class assignment operator is always hidden. If a using-declaration is used to bring in the assignment operator from the base class, and its argument type could be the same as the argument type of the implicit assignment operator of the derived class, the using-declaration is also hidden by the implicit declaration.

[ edit ] Implicitly-defined copy assignment operator

If the implicitly-declared copy assignment operator is neither deleted nor trivial, it is defined (that is, a function body is generated and compiled) by the compiler if odr-used or needed for constant evaluation (since C++14) . For union types, the implicitly-defined copy assignment copies the object representation (as by std::memmove ). For non-union class types, the operator performs member-wise copy assignment of the object's direct bases and non-static data members, in their initialization order, using built-in assignment for the scalars, memberwise copy-assignment for arrays, and copy assignment operator for class types (called non-virtually).

[ edit ] Deleted copy assignment operator

An implicitly-declared or explicitly-defaulted (since C++11) copy assignment operator for class T is undefined (until C++11) defined as deleted (since C++11) if any of the following conditions is satisfied:

  • T has a non-static data member of a const-qualified non-class type (or possibly multi-dimensional array thereof).
  • T has a non-static data member of a reference type.
  • T has a potentially constructed subobject of class type M (or possibly multi-dimensional array thereof) such that the overload resolution as applied to find M 's copy assignment operator
  • does not result in a usable candidate, or
  • in the case of the subobject being a variant member , selects a non-trivial function.

[ edit ] Trivial copy assignment operator

The copy assignment operator for class T is trivial if all of the following is true:

  • it is not user-provided (meaning, it is implicitly-defined or defaulted);
  • T has no virtual member functions;
  • T has no virtual base classes;
  • the copy assignment operator selected for every direct base of T is trivial;
  • the copy assignment operator selected for every non-static class type (or array of class type) member of T is trivial.

A trivial copy assignment operator makes a copy of the object representation as if by std::memmove . All data types compatible with the C language (POD types) are trivially copy-assignable.

[ edit ] Eligible copy assignment operator

Triviality of eligible copy assignment operators determines whether the class is a trivially copyable type .

[ edit ] Notes

If both copy and move assignment operators are provided, overload resolution selects the move assignment if the argument is an rvalue (either a prvalue such as a nameless temporary or an xvalue such as the result of std::move ), and selects the copy assignment if the argument is an lvalue (named object or a function/operator returning lvalue reference). If only the copy assignment is provided, all argument categories select it (as long as it takes its argument by value or as reference to const, since rvalues can bind to const references), which makes copy assignment the fallback for move assignment, when move is unavailable.

It is unspecified whether virtual base class subobjects that are accessible through more than one path in the inheritance lattice, are assigned more than once by the implicitly-defined copy assignment operator (same applies to move assignment ).

See assignment operator overloading for additional detail on the expected behavior of a user-defined copy-assignment operator.

[ edit ] Example

[ edit ] defect reports.

The following behavior-changing defect reports were applied retroactively to previously published C++ standards.

[ edit ] See also

  • converting constructor
  • copy constructor
  • copy elision
  • default constructor
  • aggregate initialization
  • constant initialization
  • copy initialization
  • default initialization
  • direct initialization
  • initializer list
  • list initialization
  • reference initialization
  • value initialization
  • zero initialization
  • move assignment
  • move constructor
  • Recent changes
  • Offline version
  • What links here
  • Related changes
  • Upload file
  • Special pages
  • Printable version
  • Permanent link
  • Page information
  • In other languages
  • This page was last modified on 2 February 2024, at 15:13.
  • This page has been accessed 1,333,785 times.
  • Privacy policy
  • About cppreference.com
  • Disclaimers

Powered by MediaWiki

Overloading assignments (C++ only)

  • Copy assignment operators (C++ only)
  • Assignment operators

Learn C++ practically and Get Certified .

Popular Tutorials

Popular examples, reference materials, learn c++ interactively, introduction to c++.

  • Getting Started With C++
  • Your First C++ Program
  • C++ Comments

C++ Fundamentals

  • C++ Keywords and Identifiers
  • C++ Variables, Literals and Constants
  • C++ Data Types
  • C++ Type Modifiers
  • C++ Constants
  • C++ Basic Input/Output
  • C++ Operators

Flow Control

  • C++ Relational and Logical Operators
  • C++ if, if...else and Nested if...else
  • C++ for Loop
  • C++ while and do...while Loop
  • C++ break Statement
  • C++ continue Statement
  • C++ goto Statement
  • C++ switch..case Statement

C++ Ternary Operator

  • C++ Functions
  • C++ Programming Default Arguments

C++ Function Overloading

  • C++ Inline Functions
  • C++ Recursion

Arrays and Strings

  • C++ Array to Function
  • C++ Multidimensional Arrays
  • C++ String Class

Pointers and References

  • C++ Pointers
  • C++ Pointers and Arrays
  • C++ References: Using Pointers
  • C++ Call by Reference: Using pointers
  • C++ Memory Management: new and delete

Structures and Enumerations

  • C++ Structures
  • C++ Structure and Function
  • C++ Pointers to Structure
  • C++ Enumeration

Object Oriented Programming

  • C++ Classes and Objects
  • C++ Constructors
  • C++ Constructor Overloading
  • C++ Destructors
  • C++ Access Modifiers
  • C++ Encapsulation
  • C++ friend Function and friend Classes

Inheritance & Polymorphism

  • C++ Inheritance
  • C++ Public, Protected and Private Inheritance
  • C++ Multiple, Multilevel and Hierarchical Inheritance
  • C++ Function Overriding
  • C++ Virtual Functions
  • C++ Abstract Class and Pure Virtual Function

STL - Vector, Queue & Stack

  • C++ Standard Template Library
  • C++ STL Containers
  • C++ std::array
  • C++ Vectors
  • C++ Forward List
  • C++ Priority Queue

STL - Map & Set

  • C++ Multimap
  • C++ Multiset
  • C++ Unordered Map
  • C++ Unordered Set
  • C++ Unordered Multiset
  • C++ Unordered Multimap

STL - Iterators & Algorithms

  • C++ Iterators
  • C++ Algorithm
  • C++ Functor

Additional Topics

  • C++ Exceptions Handling
  • C++ File Handling
  • C++ Ranged for Loop
  • C++ Nested Loop
  • C++ Function Template
  • C++ Class Templates
  • C++ Type Conversion
  • C++ Type Conversion Operators

C++ Operator Overloading

Advanced topics.

  • C++ Namespaces
  • C++ Preprocessors and Macros
  • C++ Storage Class
  • C++ Bitwise Operators
  • C++ Buffers
  • C++ istream
  • C++ ostream

C++ Tutorials

  • Subtract Complex Number Using Operator Overloading
  • Increment ++ and Decrement -- Operator Overloading in C++ Programming
  • Add Complex Numbers by Passing Structure to a Function

C++ Polymorphism

C++ Operator Precedence and Associativity

In C++, we can define how operators behave for user-defined types like class and structures For example,

The + operator, when used with values of type int , returns their sum. However, when used with objects of a user-defined type, it is an error.

In this case, we can define the behavior of the + operator to work with objects as well.

This concept of defining operators to work with objects and structure variables is known as operator overloading .

  • Syntax for C++ Operator Overloading

The syntax for overloading an operator is similar to that of function with the addition of the operator keyword followed by the operator symbol.

  • returnType - the return type of the function
  • operator - a special keyword
  • symbol - the operator we want to overload ( + , < , - , ++ , etc.)
  • arguments - the arguments passed to the function
  • Overloading the Binary + Operator

Following is a program to demonstrate the overloading of the + operator for the class Complex .

Here, we first created a friend function with a return type Complex .

The operator keyword followed by + indicates that we are overloading the + operator.

The function takes two arguments:

  • Complex& indicates that we are passing objects by reference and obj1 and obj2 are references to Complex objects. This is an efficient approach because it avoids unnecessary copying, especially for large objects. To learn more, visit C++ References .
  • const indicates that referenced objects are constant, meaning we cannot modify obj1 and obj2 within the function.

Inside the function, we created another Complex object, temp to store the result of addition.

We then add the real parts of two objects and store it into the real attribute of the temp object.

Similarly, we add the imaginary parts of the two objects and store them into the img attribute of the temp object.

At last, we return the temp object from the function.

We can also overload the operators using a member function instead of a friend function. For example,

In this case, the operator is invoked by the first operand. Meaning, the line

translates to

Here, the number of arguments to the operator function is reduced by one because the first argument is used to invoke the function.

The problem with this approach is, not all the time the first operand is an object of a user-defined type. For example:

That's why it is recommended to overload operator functions as a non-member function generally, defined as a friend function.

  • Overloading ++ as a Prefix Operator

Following is a program to demonstrate the overloading of the ++ operator for the class Count .

Here, when we use ++count1; , the void operator ++ () is called. This increases the value attribute for the object count1 by 1.

Note : When we overload operators, we can use it to work in any way we like. For example, we could have used ++ to increase value by 100.

However, this makes our code confusing and difficult to understand. It's our job as a programmer to use operator overloading properly and in a consistent and intuitive way.

To overload the ++ operator as a Postfix Operator, we declare a member function operator++() with one argument having type int .

Here, when we use count1++; , the void operator ++ (int) is called. This increments the value attribute for the object count1 by 1.

Note : The argument int is just to indicate that the operator is used as a postfix operator.

  • Things to Remember in C++ Operator Overloading

1. By default, operators = and & are already overloaded in C++. For example,

we can directly use the = operator to copy objects of the same class. Here, we do not need to create an operator function.

2. We cannot change the precedence and associativity of operators using operator overloading.

3. We cannot overload following operators in C++:

  • :: (scope resolution)
  • . (member selection)
  • .* (member selection through pointer to function)
  • ?: (ternary operator)
  • sizeof operator
  • typeid Operator

4. We cannot overload operators for fundamental data types like int , float , etc

  • How to overload increment operator in right way?
  • How to overload binary operator - to subtract complex numbers?
  • Increment ++ and Decrement -- Operators

Table of Contents

  • Introduction

Sorry about that.

Related Tutorials

C++ Tutorial

  • C++ Classes and Objects
  • C++ Polymorphism
  • C++ Inheritance
  • C++ Abstraction
  • C++ Encapsulation
  • C++ OOPs Interview Questions
  • C++ OOPs MCQ
  • C++ Interview Questions
  • C++ Function Overloading
  • C++ Programs
  • C++ Preprocessor
  • C++ Templates
  • Types of Operator Overloading in C++
  • Overloading of function-call operator in C++
  • Overloading New and Delete operator in c++
  • Operator Overloading in C++
  • Typecast Operator Overloading in C++
  • Increment (++) and Decrement (--) Operator Overloading in C++
  • Overloading stream insertion (<>) operators in C++
  • Rules for operator overloading
  • Overloading Relational Operators in C++
  • Input/Output Operators Overloading in C++
  • C++ Assignment Operator Overloading
  • C++ Bitwise Operator Overloading
  • How to Overload == Operator in C++?
  • Different ways of Method Overloading in Java
  • Operator Overloading in Dart
  • Operator Overloading in Ruby
  • Operator Overloading in Julia
  • Kotlin Operator Overloading
  • Method Overloading in Different Classes in Java

Different Ways of Operator Overloading in C++

In C++, operator overloading is the concept that allows us to redefine the behavior of the already existing operator for our class. C++ provides a special function called operator function that can be used to achieve operator overloading.

In this article, we will learn the different ways in which we can define the operator function for operator overloading in C++.

We can define the operator function as the following three functions:

  • Operator Overloading using Friend Function
  • Operator Overloading using Member Function
  • Operator Overloading using Global Non-Friend Function

1. Operator Overloading Using Friend Function

Similar to the above approach where we defined the overload function outside the class definition, we can define that function as a friend when we want our operator function to modify the value of the private data members.

Again, the binary operator function will take two arguments and the unary operator function will take one argument as the function is defined outside the class and there will be no this pointer.

Note: Apart from the case where we need the operator function to give access to the private memebers, we should not use the friend function to prevent the exposure of private members to public API.

E xample of Operator Overloading Using Friend Function

Operators that cannot be overloaded when declaring that function as friend function are = () [] -> .

2. Overloading Operator Using Member Function

In this method, we create a member operator function defined inside the class. It is one of the simplest and most straightforward methods of operator overlading.

Here, the operator function takes one less argument as compared to the global operator overloads. For the binary operator, one argument will be the *this object, and the other will be taken as an argument. For unary, only * this object will be used.

Note: The operator function must ber a non-static (member function)

Example of Overloading Operator Using Non-Static Member Function

Explanation: In the above program, it shows that no argument is passed and no return_type value is returned, because the unary operator works on a single operand. (-) operator changes the functionality to its member function. For the (+) operator, one argument was passed and it returned an object of the same type with values of them added.

Note:  d2 = -d1 will not work, because operator-() does not return any value.

3. Overloading Operator Using Global Function

We can also overload an operator as the global function which is not a friend of the class. The compiler will find the overload by matching the types of the argument. If there are multiple matching operator overloads, then it will throw an ambiguity error.

Now, the global binary operator function will take two arguments, while the global unary operator function will take a single argument.

Example of Overloading Operator Using Global Function

Explanation: Here, d1 calls the operator function of its class object and takes d2 as a parameter, by which the operator function returns the object and the result will reflect in the d3 object.

It is generally preferred to overload binary operator as global function. It is because in global function, both the object or the value that can be converted to the object can be used as either left or right operand and it will work. For member operator function, it won’t work if the value that can be converted to object is used as left operand. For Example,

We overload the relational operator < for our class, then

Please Login to comment...

Similar reads.

  • cpp-overloading

Improve your Coding Skills with Practice

 alt=

What kind of Experience do you want to share?

IMAGES

  1. How to work with operator overloading in C#

    overloaded assignment operator in c

  2. Matrix addition using operator overloading in c

    overloaded assignment operator in c

  3. Assignment Operator Overloading In C

    overloaded assignment operator in c

  4. Assignment operator overloading in c++

    overloaded assignment operator in c

  5. Assignment Operator Overloading in C++

    overloaded assignment operator in c

  6. C# Operator Overloading

    overloaded assignment operator in c

VIDEO

  1. assignment Operator C Language in Telugu

  2. OR Operator C

  3. Overloading operators

  4. What is operator overloading in C++?

  5. 14. Assignment Operator

  6. Assignment Operator in C Programming

COMMENTS

  1. 21.12

    21.12 — Overloading the assignment operator. Alex November 27, 2023. The copy assignment operator (operator=) is used to copy values from one object to another already existing object. As of C++11, C++ also supports "Move assignment". We discuss move assignment in lesson 22.3 -- Move constructors and move assignment .

  2. C++ Assignment Operator Overloading

    The assignment operator,"=", is the operator used for Assignment. It copies the right value into the left value. Assignment Operators are predefined to operate only on built-in Data types. Assignment operator overloading is binary operator overloading. Overloading assignment operator in C++ copies all values of one object to another object.

  3. Assignment operators

    for assignments to class type objects, the right operand could be an initializer list only when the assignment is defined by a user-defined assignment operator. removed user-defined assignment constraint. CWG 1538. C++11. E1 ={E2} was equivalent to E1 = T(E2) ( T is the type of E1 ), this introduced a C-style cast. it is equivalent to E1 = T{E2}

  4. assignment operator overloading in c++

    There are no problems with the second version of the assignment operator. In fact, that is the standard way for an assignment operator. Edit: Note that I am referring to the return type of the assignment operator, not to the implementation itself. As has been pointed out in comments, the implementation itself is another issue.

  5. operator overloading

    The assignment operator (operator =) has special properties: ... user-defined classes that are intended to be used in boolean contexts could provide only operator bool and need not overload operator!. (since C++11) Rarely overloaded operators. The following operators are rarely overloaded:

  6. Operator Overloading

    Overloaded operators are implemented as functions. The name of an overloaded operator is operator x, where x is the operator as it appears in the following table. For example, to overload the addition operator, you define a function called operator+. Similarly, to overload the addition/assignment operator, +=, define a function called operator+=.

  7. When should we write our own assignment operator in C++?

    1) Do not allow assignment of one object to other object. We can create our own dummy assignment operator and make it private. 2) Write your own assignment operator that does deep copy. Same is true for Copy Constructor. Following is an example of overloading assignment operator for the above class. #include<iostream>.

  8. operator overloading

    Commonly overloaded operators have the following typical, canonical forms: Assignment operator. The assignment operator (operator =) has special properties: see copy assignment and move assignment for details. The canonical copy-assignment operator is expected to perform no action on self-assignment, and to return the lhs by reference:

  9. Copy Constructor vs Assignment Operator in C++

    C++ compiler implicitly provides a copy constructor, if no copy constructor is defined in the class. A bitwise copy gets created, if the Assignment operator is not overloaded. Consider the following C++ program. Explanation: Here, t2 = t1; calls the assignment operator, same as t2.operator= (t1); and Test t3 = t1; calls the copy constructor ...

  10. C++ Programming/Operators/Operator Overloading

    Using operator overloading permits a more concise way of writing it, like this: a + b * c (Assuming the * operator has higher precedence than +.). Operator overloading can provide more than an aesthetic benefit, since the language allows operators to be invoked implicitly in some circumstances.

  11. Mastering Operator Overloads: A Comprehensive Guide

    Code Explanation: The program defines a class ComplexNumber to represent complex numbers and provide operator overloads for common mathematical operations. The __init__ method initializes each complex number with a real and an imaginary component. The __repr__ method allows us to print complex number objects in a way that's human-readable ...

  12. Assignment Operator Overload in c++

    An overloaded assignment operator should look like this: Complex &Complex::operator=(const Complex& rhs) {. real = rhs.real; imaginary = rhs.imaginary; return *this; }; You should also note, that if you overload the assignment operator you should overload the copy constructor for Complex in the same manner:

  13. Copy assignment operator

    Triviality of eligible copy assignment operators determines whether the class is a trivially copyable type. [] NoteIf both copy and move assignment operators are provided, overload resolution selects the move assignment if the argument is an rvalue (either a prvalue such as a nameless temporary or an xvalue such as the result of std::move), and selects the copy assignment if the argument is an ...

  14. Overloading assignments (C++ only)

    Overloading assignments (C++ only) You overload the assignment operator, operator=, with a nonstatic member function that has only one parameter. You cannot declare an overloaded assignment operator that is a nonmember function. The following example shows how you can overload the assignment operator for a particular class: struct X {. int data;

  15. C++ Operator Overloading (With Examples)

    Things to Remember in C++ Operator Overloading. 1. By default, operators = and & are already overloaded in C++. For example, we can directly use the = operator to copy objects of the same class. Here, we do not need to create an operator function. 2. We cannot change the precedence and associativity of operators using operator overloading.

  16. Operators in C and C++

    Assignment operators. All assignment expressions exist in C and C++ and can be overloaded in C++. For the given operators the semantic of the built-in combined assignment expression a ⊚= b is equivalent to a = a ⊚ b, except that a is evaluated only once. Operator name

  17. Operator Overloading in C++

    C++ Operator Overloading. C++ has the ability to provide the operators with a special meaning for a data type, this ability is known as operator overloading. Operator overloading is a compile-time polymorphism. ... Assignment Operator: Compiler automatically creates a default assignment operator with every class. The default assignment operator ...

  18. c++

    4. Correct me if I'm wrong: I understand that when having a class with members that are pointers, a copy of a class object will result in that the pointers representing the same memory address. This can result in changes done to one class object to affect all copies of this object. A solution to this can be to overload the = operator.

  19. [PATCH] c++: lvalueness of non-dependent assignment [PR114994]

    For trunk as a follow-up I can implement the > > mentionted representation change to use CALL_EXPR instead of > > MODOP_EXPR for a non-dependent simple assignment expression that > > resolved to an operator= overload. > > > > -- >8 -- > > > > r14-4111 made us check non-dependent assignment expressions ahead of > > time

  20. Overloading assignment operator for Stack in C++

    b=a is invoking the assignment operator, not the copy constructor. Your supplied code example doesn't include an assignment operator, operator=(). Your assignment operator should include essentially the same logic as your copy constructor so you'd be best to move that logic to a new function and have both the copy constructor and assignment ...

  21. string class assignment operator overloading in c++

    1) Use "rhs" (right-hand-side) instead of "str" for your variable name to avoid ambiguity. 2) Always check if your object is not being assigned to itself. 3) Release the old allocated memory before allocating new. 4) Copy over the contents of rhs to this->str, instead of just redirecting pointers.

  22. Different Ways of Operator Overloading in C++

    Output. Total Feet & Inches: 18'11. Operators that cannot be overloaded when declaring that function as friend function are = () [] ->. 2. Overloading Operator Using Member Function. In this method, we create a member operator function defined inside the class. It is one of the simplest and most straightforward methods of operator overlading.

  23. c++

    I want to overload assigning a value to an overloaded index in a c++ class. Here is my code so far: #include <iostream> #include <vector> #include <string> using namespace std; cl...