Till now, we have read that C++ supports two types of variables:
Reference can be created by simply using an ampersand (&) operator. When we create a variable, then it occupies some memory location. We can create a reference of the variable; therefore, we can access the original variable by using either name of the variable or reference. For example,
int a=10;
Now, we create the reference variable of the above variable.
int &ref=a;
The above statement means that 'ref' is a reference variable of 'a', i.e., we can use the 'ref' variable in place of 'a' variable.
C++ provides two types of references:
It can be declared by using & operator with the reference type variable.
#include <iostream> using namespace std; int main() { int a=10; int &value=a; std::cout << value << std::endl; return 0; }
References as aliases is another name of the variable which is being referenced.
For example,
int a=10; // 'a' is a variable. int &b=a; // 'b' reference to a. int &c=a; // 'c' reference to a.
Let's look at a simple example.
#include <iostream> using namespace std; int main() { int a=70; // variable initialization int &b=a; int &c=a; std::cout << "Value of a is :" <<a<< std::endl; std::cout << "Value of b is :" <<b<< std::endl; std::cout << "Value of c is :" <<c<< std::endl; return 0;}
In the above code, we create a variable 'a' which contains a value '70'. We have declared two reference variables, i.e., b and c, and both are referring to the same variable 'a'. Therefore, we can say that 'a' variable can be accessed by 'b' and 'c' variable.
The following are the properties of references:
It must be initialized at the time of the declaration.
#include <iostream> using namespace std; int main() { int a=10; // variable initialization int &b=a; // b reference to a std::cout << "value of a is " <<b<< std::endl; return 0; }
In the above code, we have created a reference variable, i.e., 'b'. At the time of declaration, 'a' variable is assigned to 'b'. If we do not assign at the time of declaration, then the code would look like:
int &b; &b=a;
The above code will throw a compile-time error as 'a' is not assigned at the time of declaration.
It cannot be reassigned means that the reference variable cannot be modified.
#include <iostream> using namespace std; int main() { int x=11; // variable initialization int z=67; int &y=x; // y reference to x int &y=z; // y reference to z, but throws a compile-time error. return 0;}
In the above code, 'y' reference variable is referring to 'x' variable, and then 'z' is assigned to 'y'. But this reassignment is not possible with the reference variable, so it throws a compile-time error.
main.cpp: In function 'int main()': main.cpp:18:9: error: redeclaration of 'int& y' int &y=z; // y reference to z, but throws a compile-time error. ^ main.cpp:17:9: note: 'int& y' previously declared here int &y=x; // y reference to x ^
References can also be passed as a function parameter. It does not create a copy of the argument and behaves as an alias for a parameter. It enhances the performance as it does not create a copy of the argument.
Let's understand through a simple example.
#include <iostream> using namespace std; int main() { int a=9; // variable initialization int b=10; // variable initialization swap(a, b); // function calling std::cout << "value of a is :" <<a<< std::endl; std::cout << "value of b is :" <<b<< std::endl; return 0; } void swap(int &p, int &q) // function definition { int temp; // variable declaration temp=p; p=q; q=temp; }
In the above code, we are swapping the values of 'a' and 'b'. We have passed the variables 'a' and 'b' to the swap() function. In swap() function, 'p' is referring to 'a' and 'q' is referring to 'b'. When we swap the values of 'p' and 'q' means that the values of 'a' and 'b' are also swapped.
With the help of references, we can easily access the nested data.
#include <iostream> using namespace std; struct profile { int id; }; struct employee { profile p; }; int main() { employee e; int &ref=e.p.id; ref=34; std::cout << e.p.id << std::endl; }
In the above code, we are trying to access the 'id' of the profile struct of the employee. We generally access this member by using the statement e.p.id, but this would be a tedious task if we have multiple access to this member. To avoid this situation, we create a reference variable, i.e., ref, which is another name of 'e.p.id'.