是否可以从初始化的子类中返回超类对象而无需初始化超类

时间:2018-12-07 22:05:36

标签: java

我有以下代码:

public class Person
{
    final String firstName;
    final String lastName;
    final int age;
    final UUID identification;

    public Person(final String firstName, final String lastName, final int age)
    {
        this.firstName = firstName;
        this.lastName = lastName;
        this.age = age;
        this.identification = UUID.randomUUID();
    }

    protected Person(final String firstName, final String lastName, final int age, final UUID identification)
    {
        this.firstName = firstName;
        this.lastName = lastName;
        this.age = age;
        this.identification = identification;
    }

    /*
        Getter functions 
    */

    public Person asPerson()
    {
        return this;
    }

    /*
        Hash and Equals code
        Equals checks for first/lastName, age, and identification
    */
}

public class Employee extends Person
{
    final String occupation;
    final float salary;

    public Employee(final String firstName, final String lastName, final int age, final String occupation, final float salary)
    {
        super(firstName, lastName, age);
        this.occupation = occupation;
        this.salary = salary;
    }

    public Employee(final Person person, final String occupation, final float salary)
    {
        super(person.getFirstName(), person.getLastName, person.getAge(), person.getID());
        this.occupation = occupation;
        this.salary = salary;
    }

    /*
        Getter functions for occupation and salary
    */

    @Override
    public Person asPerson()
    {
        return new Person(firstName, lastName, age, identification);
    }

    /*
        Hash and Equals code
        Equals checks for equality in occupation and salary
    */
}

public class Volunteer extends Person
{
    final String location;

    public Volunteer(final String firstName, final String lastName, final int age, final String location)
    {
        super(firstName, lastName, age);
        this.location = location;
    }

    public Volunteer(final Person person, final String location)
    {
        super(person.getFirstName(), person.getLastName(), person.getAge(), person.getID());
        this.location = location;
    }

    /*
        Getter for location
    */

    @Override
    public Person asPerson()
    {
        return new Person(firstName, lastName, age, identification);
    }

    /*
        Hash and Equals
        Equals checks for equality in location.
    */
}

public Main
{
    public static void main(String[] args)
    {
        final Person person = new Person("Man", "Fredman", 25);
        final Person employee = new Employee(person, "Driver", 65000.0f);
        final Person volunteer = new Volunteer(person, "Philly");

        final boolean eqality = compareVtoE(volunteer, employee);

        System.out.println(equality);
    }

    private boolean compareVtoE(final Person volunteer, final Person employee)
    {
        return volunteer.asPerson().equals(employee.asPerson());
    }
}

已经定义了Employee变量,asPerson中的Employee函数中是否有一种方法可以返回超类实例而不必调用new Person(...)

我目前的解决方法是使用受保护的构造函数来加入identification,但是我认为有更好的方法来解决这个问题。

修改

我已经扩展了示例。假设我有一个Volunteer和一个Employee,它们都扩展了Person并且可以在构造函数中加入一个Person对象。他们可以是同一个人,但做不同的事情。要查看一个志愿者是否与雇员相同,我需要一种方法来获取Person对象,而无需更改UUID。我的解决方法是在Person中使用受保护的构造函数,该构造函数接受UUID,该UUID在super的子类构造函数中使用。我想避免在asPerson()中使用构造函数,而创建Person的新实例。

1 个答案:

答案 0 :(得分:0)

我很确定没有办法完成您要的操作,因为它需要更改对象而不更改它,但是这是比较问题的两种可能的解决方案:

  1. 重写equals类中的Person方法,以便您可以比较人员而不管他们的角色(雇员或志愿者):

    @Override
    public boolean equals(Object other) {
        if (other instanceof Person) {
            return identification.equals(((Person)other).identification);
        }
    
        return false;
    }
    
  2. 如果由于某种原因您不能使用equals,例如您需要在具有不同功能的派生类中覆盖它,只需创建一个isSamePerson函数,如下所示:

    public boolean isSamePerson(Person other) {
        if (other != null) return identification.equals(other.identification);
        return false;
    }
    

这将为您节省不必要的对象重复,并避免失去人们的踪迹。