Approach 1:
class Employee
{
public:
virtual int calculateSalary() = 0;
};
class PermanentEmployee : public Employee {
const int salaryPerMonth;
public:
PermanentEmployee(int sal) : salaryPerMonth(sal){}
int calculateSalary() {
return salaryPerMonth;
}
};
class ContractEmployee : public Employee {
const int wagesPerHr;
int totalHour;
public:
ContractEmployee(int sal) : wagesPerHr(sal), totalHour(0){}
void setWorkingDuration(int time) {
totalHour = totalHour + time;
}
int calculateSalary() {
return wagesPerHr * totalHour;
}
};
class Manager {
list<Employee *> ls;
public:
void assignWorkingHour() {
list<Employee *>::iterator it;
for(it = ls.begin(); it != ls.end(); it++) {
Employee *emp = *it;
ContractEmployee* contractEmp = dynamic_cast<ContractEmployee* >(emp);
if(contractEmp) {
contractEmp->setWorkingDuration(5);
}
}
}
};
In problem, there are 2 type of Employee
: PermanentEmployee
and ContractEmployee
.
There is a class called Manager
which contains a list of all employee working under him.
For ContractEmployee
, it has to invoke function setWorkingDuration()
, which is being invoked in method assignWorkingHour
of class Manager
.
The problem is:
Here type of Employee
is being determind by dynamic_cast
operator and Manager
has to know about all type of derive class of Employee
.
Approach 2:
Add another member in class Employee
:
enum TypeOfEmployee {CONTRACT, PERMANENT};
and check TypeOfEmployee
to determine the type of Employee
Please tell me which is better or is there any alternative approach?
The GetType method is inherited by all types that derive from Object. This means that, in addition to using your own language's comparison keyword, you can use the GetType method to determine the type of a particular object, as the following example shows.
The java. lang. Object. getClass() method is used to determine the type of object at run time.
To get the type of a variable in Python, you can use the built-in type() function. In Python, everything is an object. So, when you use the type() function to print the type of the value stored in a variable to the console, it returns the class type of the object.
The better approach is to write code that doesn't require knowledge about the exact object type. Seems to me the most elegant way to deal with this is to move the setWorkingDuration()
to the employee class. Probably like this:
class Employee
{
public:
// Calculates the salary for this employee.
// Returns the calculated salary.
virtual int calculateSalary() = 0;
// Sets the working duration. Does nothing if the employee is permanent.
// Returns true if Employee is on a contract, false if permanent.
virtual bool setWorkingDuration(int time)
{
return false;
}
};
class PermanentEmployee : public Employee
{
const int salaryPerMonth;
public:
PermanentEmployee(int sal) : salaryPerMonth(sal) {}
int calculateSalary()
{
return salaryPerMonth;
}
};
class ContractEmployee : public Employee
{
const int wagesPerHr;
int totalHour;
public:
ContractEmployee(int sal) : wagesPerHr(sal), totalHour(0) {}
int calculateSalary()
{
return wagesPerHr * totalHour;
}
bool setWorkingDuration(int time)
{
totalHour = totalHour + time;
return true;
}
};
class Manager
{
list<Employee *> ls;
public:
void assignWorkingHours()
{
list<Employee *>::iterator it;
for(it = ls.begin(); it != ls.end(); it++)
{
Employee* emp = *it;
emp->setWorkingDuration(5);
}
}
};
This way, the Manager
class doesn't have to know whether the Employee
is actually a PermanentEmployee
or a ContractEmployee
. That is what polymorphism gives you. Generally speaking if you have to use dynamic_cast<>
, you may want to take another look at the design and see if you can omit it.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With