What is Operator Overloading?
We know that standard data types supplied by languages are well known and there will be operators like +,* ,% that operates on these data types. But, what is the case if it is user-defined types say a 3dpoint class, which is the combination of three integers. Well, all languages that supports operator overloading says, "It is you Type. Please you say how the operator + should work".
If you say "How the Operator + should work for 3point class", then you are overloading + operator. Because, it will now know how to add two integers and how to add two 3dpoints.
Below are the types of overloading that I will demonstrate in this article:
- Implicit Conversion Operator
- Explicit Conversion Operator
- Binary Operator
Let us start with TimeHHMMSS class
Before we move on to the Overloading, first let me explain what this class will do. The class is used to store the time in Hour, Minute and Seconds. There are three members defined for that. The class Looks Like:
class TimeHHMMSS
{
//001: Parts of the time class
public int m_hour;
public int m_minute;
public int m_sec;
The default constructor will set all the members to zero. And a overloaded version will accept hour, minute and second. Below is the code for Constructors:
//002: Default constructor for the class
public TimeHHMMSS()
{
m_hour = 0;
m_minute = 0;
m_sec = 0;
}
//003: Overloaded Constructor
public TimeHHMMSS(int hr, int min, int sec)
{
m_hour = hr;
m_minute = min;
m_sec = sec;
}
All classes in C# have Object as their base class. We will override the ToString method our own way.
//004: Every class that we create has Object as the base class. Override the ToString
public override string ToString()
{
return string.Format("{0}:{1}:{2}", m_hour, m_minute, m_sec);
}
Implicit Conversion โ (A) Integer to TimeHHMMSS
Below is the Syntax for Implicit conversion:
public static implicit operator <Convert to> (<ConvertFrom> Variable)
We will get the integer as parameter. So the time is specified in smaller units say in seconds passed as an integer parameter. 1 Hour, 10 minutes, 15 Seconds can be specified in seconds as 4215. These "seconds" taken as an integer parameter is processed to split into Hours, Minutes and Seconds. After the Split, we have all the member variables of the class ready to return back. Below is the Conversion operator:
//005: Implicit Conversion Operator. Coversion from int to TimeHHMMSS
public static implicit operator TimeHHMMSS(int totalSeconds)
{
//005_1 : Declarations
int hour, min, seconds;
int RemainingSeconds;
TimeHHMMSS returnobject = new TimeHHMMSS();
//005_2: Calculate Seconds
seconds = totalSeconds % 60;
returnobject.m_sec = seconds;
//005_3: Calculate Minutes
RemainingSeconds = totalSeconds - seconds;
min = RemainingSeconds % ( 60 * 60 ); //Calculated minutes in terms of seconds
returnobject.m_minute = min / 60 ;
//005_4: Calculate Hours
RemainingSeconds = totalSeconds - ( returnobject.m_minute * 60 + returnobject.m_sec );
hour = RemainingSeconds % (60 * 60 * 24 ); // Hour in Seconds
returnobject.m_hour = hour / 3600;
return returnobject;
}
OK, how is the above operator used? If we assume t2 is the TimeHHMMSS object constructed using the default constructor the below statement will invoke the implicit conversion overloaded
t2 = 33175;
Implicit Conversion โ (B) TimeHHMMSS to Integer
Now, we will implement the same implicit conversion in the reverse; that is, we will make conversion from Time Object to integer. I hope as you looked at the previous function, you will know what the implementation is. Below is the function:
//006: Implicit Conversion Operator. Conversion from TimeHHMMSS to integer
public static implicit operator int(TimeHHMMSS time)
{
return (time.m_hour * 60 * 60) + (time.m_minute * 60 ) + time.m_sec ;
}
When will the calling code invoke the above implicit conversion? The code is below:
int timeinSeconds;
timeinSeconds = t2;
Explicit Conversion- Conversion from Float to TimeHHMMSS
In the above conversion we saw that the conversion takes place even when we do not explicitly specify that. The way we implement the Time class is we recommend integer data type, so we make the conversion for integer implicit. For a float data type we will implement (Not actually an implementation, we will handle if a user accidentally make an float conversion explicitly, and re-direct to int implicit conversion).
Below is the code that will take a float, re-directs to integer implicit conversion. From the client point of view it is an explicit conversion:
//007: Explicit Conversion Operator. Conversion from float to TimeHHMMSS.
public static explicit operator TimeHHMMSS(float totalSeconds) // We don't want to handle fraction in Seconds (Micro Sec or nano Sec stc)
{
TimeHHMMSS returnobject = new TimeHHMMSS();
returnobject = (int) totalSeconds; //Makes a call to implicit convertion : int->TimeHHMMSS
return returnobject;
}
Below is the piece of client code, which will make a call to our explicit overloaded operator:
TimeHHMMSS t3 = (TimeHHMMSS) 23213.67f;
Binary Operator Overloading โ Overload + operator
Now, it is time to overload the binary operator +. With this we can add two TimeHHMMSS class and get back the added TimeHHMMSS.
The caller will write a statement something like the one below:
TimeHHMMSS t4 = t1 + t2;
Our + overloading function will take TimeHHMMSS t1,t2 as two parameters in the same order; that is t1 as first parameter and t2 as second parameter. Then, the added TimeHHMMSS is returned back to the t4 object of the same type.
We will use the implicit Time->Integer conversion on t1 and t2. Add the integer values then return the added value. Since, the return type we specify as TimeHHMMSS, Once again an implicit conversion in reverse direction takes place; that a conversion from integer->TimeHHMMSS. The overloaded + operator is shown below:
//008: Operator Overloading +. Binary Operator.
public static TimeHHMMSS operator+ (TimeHHMMSS operandLH, TimeHHMMSS OperandRH)
{
//008_1: Get the Seconds and Add.
int totalSeconds, LHS_Seconds, RHS_Seconds;
LHS_Seconds = operandLH; //Implicit convertion: Time -> int
RHS_Seconds = OperandRH; //Implicit convertion: Time -> int
totalSeconds = LHS_Seconds + RHS_Seconds;
//008_2: Return the Seconds. Required return type is TimeHHMMSS,
// what we return is integer. Again one more implicit conevrtion in reverse
return totalSeconds; //Implicit convertion: int -> Time
}
Closing Notes:
1. The binary operator will work for the following statements also:
t4 = t4 + 4215;
t4 = t4 + (TimeHHMMSS) 54321.456f ;
Debug to see what kind of conversion takes place.
2. If you overload an == operator, then you should overload !=. Same holds for operator like < and >. Etc
Hope you like this article.