Title: Inheritance Object Class
Course: CPS 161: An Intro to Programming with Java - DL MM MASTER

Inheritance Object class

Object class

1. All classes are derived from Object even if there is no extends keyword. My claim is that following 2 versions of the Person class are really the same:
Person.java - The normal way you see it


    public class Person {

    private String name;
    private int age;

    Person(String n, int a)
    {
        name=n;
        age = a;
    }

}


Person.java - Equivalent and more Explicit version


import java.lang.*;

public class Person extends Object{

    private String name;
    private int age;

    Person(String n, int a)
    {
        name=n;
        age = a;
    }

}


2. Take a look at the definition of the Object class in the Java API documention (start with package java.lang) Note the methods that all classes inherit because they are derived from Object. The ones that I want to talk about in this set of notes are:
  - boolean equals(Object)
  - String toString()
  - getClass()
3. Now consider run the following and we want to understand the results:

Why does this compile (where are toString and equals defined for Person)



public class DemoPerson {


    public static void main(String[] args) {
        Person p1 = new Person("Fred", 20);
        Person p2 = new Person("Jim", 30);
        Person p3 = new Person("Fred", 20);
        Person p4 = p1;

        System.out.println("p1="+ p1.toString());
        System.out.println("p1="+ p1);

        System.out.println("p2=" + p2);
        System.out.println("p3=" + p3);
        System.out.println("p4=" + p4);

        if (p1.equals(p2))
            System.out.println("p1 equals p2");
        else
            System.out.println("p1 does NOT equal p2");


        if (p1.equals(p3))
            System.out.println("p1 equals p3");
        else
            System.out.println("p1 does NOT equal p3");

        if (p1.equals(p4))
            System.out.println("p1 equals p4");
        else
            System.out.println("p1 does NOT equal p4");


    }

}



4. Try using the following new Person class and see that it makes things appear to work fine



public class Person {

    private String name;
    private int age;

    Person(String n, int a)
    {
        name=n;
        age = a;
    }
    public String toString()
    {
        return name + " " + age;
    }

    public boolean equals(Person p)
    {
        if (name.equals(p.name) && age == p.age)
            return true;
        else
            return false;
    }

}



5. Note that the above solution did the following:
  - We did an override of toString()
  - We did an overload of equals. There are now 2 equals methods visible to the compiler. One of them defined in Object and the other defined in Person. If you go back to when we discussed overloaded methods we said that the compiler will pick the version which is the closest fit. If we are always working with the Person class, then this will be the new equals method in most cases.
6. As you move on the more advanced Java topics like data structures, you will find that it is best to override the method in Object instead of taking the overloading method we took. So for this reason, we would then want to do the following instead:



public class Person {

    private String name;
    private int age;

    Person(String n, int a)
    {
        name=n;
        age = a;
    }
    public String toString()
    {
        return name + " " + age;
    }

    public boolean equals(Object obj)
    {
        Person p = (Person)obj;
        if (name.equals(p.name) && age == p.age)
            return true;
        else
            return false;
    }

}



7. Things that can go wrong with this approach:
  - obj can be a null
  - obj may not be a Person class so casting to a Person class causes an exception
8. Author's more robust equals method (Note that the 2 compared classes must be identical):


  public boolean equals(Object obj)
    {
        if (obj == null)
            return false;
        if (getClass() != obj.getClass())
            return false;
        Person p = (Person)obj;
        if (name.equals(p.name) && age == p.age)
            return true;
        else
            return false;
    }


9. A little looser example that may be desireable( If we had a Student class which extends Person, it is possible for the Student class to be considered equal to the Person class if the "Person parts" matched):


  public boolean equals(Object obj)
    {
        if (obj == null)
            return false;
        if (obj instanceof Person)
        {
            Person p = (Person)obj;
            if (name.equals(p.name) && age == p.age)
                return true;
        }

        return false;
    }


10. The author recommends using the getClass version because he points a lack of symmetry in the instanceof approach. To demonstrate this we will need to modify Employee and HourlyEmployee to use the intanceof approach.
Employee, HourlyEmployee code
we will need to run the following :


  Employee e = new Employee("Joe Worker", new Date("January", 1, 2004));
  HourlyEmployee hourlyE  = new HourlyEmployee("Joe Worker", new Date("January", 1, 2004),
                                                  50.50, 160);
												
	// Note that the following gives a true:
	e.equals(hourlyE);
	
	// But the following gives a false
	hourlyE.equals(e);


Keyword final ... just say No


Remember that final can be used to say that a variable can NOT be changed such as

final int num_rows = 10;






ExamplesOfFinal.java

/*
// Note String has the keyword final on it

class MyString extends String
{

}
*/
final class MyFinalClass
{
    // put anything you want in here.
}
/*
class ExtendingMyFinalClass extends MyFinalClass
{

}
*/
class ClassWithFinalMethod
{
    void normalMethod()
    {
        System.out.println("ClassWithFinalMethod.normalMethod");
    }
    final void finalMethod()
    {
        System.out.println("ClassWithFinalMethod.finalMethod");
    }
}

class ExtendingClassWithFinalMethod extends ClassWithFinalMethod
{
    void normalMethod()
    {
        System.out.println("ExtendingClassWithFinalMethod.normalMethod");
    }
    /*
    void finalMethod()
    {
        System.out.println("ExtendingClassWithFinalMethod.finalMethod");
    }
    */
}



public class ExamplesOfFinal {

    public static void main(String[] args) {
        ClassWithFinalMethod cwfm = new ClassWithFinalMethod();
        cwfm.finalMethod();
        cwfm.normalMethod();

        ExtendingClassWithFinalMethod ecwfm = new ExtendingClassWithFinalMethod();
        ecwfm.normalMethod();
    }

}



Last Modified: April 24, 2014 0:31 AM