Organize Responsibly with Methods
Not Started

Woah! Don’t slip! We still have some WET code. Take a second look at EmployeeController:

public class EmployeeController { Integer currentYear = 2023; Employee jerryEmployee = new Employee('Jerry', 2015); Integer jerryTenure= calculateTenure(jerryEmployee); Employee elaineEmployee = new Employee('Elaine', 2018); Integer elaineTenure = calculateTenure(elaineEmployee); private Integer calculateTenure(Employee emp){ Integer tenure = this.currentYear - emp.startYear; return tenure; } }

The code works fine, sure, but it’s doing too much. EmployeeController is responsible for creating an Employee object AND calculating its tenure. Yikes.

Think back to why we created the Employee class. Our goal was to encapsulate the attributes of an employee. Tenure is one of those attributes, but its calculation leaked onto the EmployeeController. It’s no longer encapsulated.

If other classes also instantiate employees and need tenure, they’d have to recreate their version of the method.

Let’s refactor for DRYer code by reassigning responsibilities. The solution is to give the Employee class the responsibility to calculate tenure. If a class like EmployeeController needs to know the tenure, it should ask the employee object.

To do this, we’ll simply move the method out of EmployeeController and into Employee:

public class Employee { String firstName; public Integer startYear {get; private set;} Employee(String firstName, Integer startYear){ firstName = firstName; startYear = startYear; } public Integer calculateTenure(Integer currentYear){ Integer tenure = currentYear - this.startYear; return tenure; } }

We’ve made some slight updates in the process. The method needs to be accessed by other classes, so it’s been marked as public. The parameters have also been updated. startYear is within scope because it’s a member variable for this class, but currentYear is not. So, the caller must provide the current year as an argument.

Now, to call this method from EmployeeController:

public class EmployeeController { Integer currentYear = 2023; Employee jerryEmployee = new Employee('Jerry', 2015); Integer jerryYearsOfEmployment = jerryEmployee.calculateTenure(currentYear); Employee elaineEmployee = new Employee('Elaine', 2018); Integer elaineYearsOfEmployment = elaineEmployee.calculateTenure(currentYear); }

The Dot Operator

Using the dot operator, we’re able to call the calculateTenure method defined in the Employee class and pass in the argument.

The dot operator is a fundamental concept in object-oriented programming. You will need it whenever you want to access another object's properties or invoke its methods. In the statement jerryEmployee.calculateTenure(currentYear), the dot operator is saying, "call the calculateTenure method that belongs to the jerryEmployee object and pass in the currentYear variable." It helps you navigate through another object to reach its properties and methods.

The keyword there being another object's properties and methods. If we wanted to call calculateTenure from the Employee constructor, we'd do so like this:

public class Employee { String firstName; public Integer startYear {get; private set;} Employee(String firstName, Integer startYear){ firstName = firstName; startYear = startYear; calculateTenure(2024); } public Integer calculateTenure(Integer currentYear){ Integer tenure = currentYear - this.startYear; return tenure; } }

There's no dot operator here because the method belongs to the same class. We only need the operator when accessing another object's properties or methods.

The ability to call methods using the dot operator is crucial for encapsulation, enabling objects to interact while maintaining their boundaries. More on that in the OOP course.

Challenge

In this version of the Contract class, the contract's activated year is passed in through the constructor.

Create a new method named calculateContractAge which accepts no parameters. The method should calculate how long a contract has been active by subtracting activatedYear from the current year, 2023. The result should be returned.

Your class will be called by code like this:

Contract nbaContract = new Contract(1997); Integer contractAge = nbaContract.calculateContractAge();