为什么使用受保护的方法而不是构造函数

时间:2015-03-01 15:28:48

标签: java

我正在做一些阅读here。用户建议

  

如果您计划进行子类化并希望验证设置器可用,   声明它保护最终而不是私人。

为什么声明一个方法 protected final ,当我可以将其声明为private并让基类中的构造函数设置变量时。

示例:

    public class Person {


        private String firstName;
        private String lastName;

        public Person(String firstname,String lastname) throws InvalidDataException
        {
            setFirstname( firstname);
            setLastname(lastname);
        }


        public void personFirstName(String firstName) throws InvalidDataException { 
            setFirstname(firstName);
        }

        public void personLastName(String lastname) throws InvalidDataException {

            setLastname(lastname);
        }

        public String getFirstName() {
            return firstName;
        }

        public String getlasttName()
        {
            return lastName;
        }

        private void setFirstname(String firstname) throws InvalidDataException{
             if( firstname == null ||firstname.length() < 1) {
                    throw new InvalidDataException("First Name Cannot be Empty");
             }
              this.firstName=firstname; 

        }

        private void setLastname(String lastname) throws InvalidDataException {

             if( lastname == null ||lastname.length() < 1) {
                    throw new InvalidDataException("Last Name Cannot be Empty");

             }

             this.lastName = lastname;
        }

    }

public class Professor extends Person {


    private String  professorID;



    public Professor(String professorID,String firstname, String lastname) throws InvalidDataException {
        super(firstname, lastname);
        // TODO Auto-generated constructor stub
        setProfessorID(professorID);
    }

    public void setID(String professorID) throws InvalidDataException{

        setProfessorID(professorID);
    }

    public String getID()
    {
        return this.professorID;
    }

    private void setProfessorID(String ID) throws InvalidDataException{
         if( ID == null ||ID.length() < 1) {
                throw new InvalidDataException("ID Cannot be Empty");
         }
          this.professorID=ID; 

    }

    public void printData()
    {
         System.out.println("Professor ID: " + this.getID() + " First Name: " + this.getFirstName() + " Last Name: " + this.getlasttName());
    }

}

我想在什么情况下声明Person中的私有方法是受保护的最终?我的子类教授可以通过基类中的构造函数访问它们。

3 个答案:

答案 0 :(得分:3)

<强> protected

protected关键字是一个访问修饰符,允许子类访问此资源。在这种情况下,方法。

<强> final

final关键字是一种多态限制,可防止子类从重新定义给定资源。同样,在这种情况下,方法。

考虑到这些定义,这会创建一个验证方法,子类仍然可以访问而无法更改它。简而言之,没有子类可以违反验证条款。通过将调用放在构造函数中,这意味着子类不能在其他任何地方进行验证调用。他们每次想要测试时都必须创建一个新对象,这显然是不可取的。

这样做可以使它更易于测试,但允许子类具有尽可能多的灵活性,同时不会破坏验证规则。

答案 1 :(得分:1)

这适用于子类应该能够设置值的情况。由于您无法预见子类,因此最好假设所有值都可以通过第三个值设置。例如,在一些文化中,女性取名为她的丈夫。例如:

public class Women extends Person {

    public void marry (Person person) {
        setLastName(person.getLastName());
    }


}

本书可能建议不要使字段受保护,毕竟每个类都必须保证其自身的状态是有效的。通过这样重写验证器,您可以从超类视角中使状态无效。

例如,假设人名不包含数字是合理的。您可以在setter-validator中实现此逻辑。但是,如果您声明字段protected,则可以推翻该字段。

像你一样制作方法public可能不值得建议,至少在一般情况下是这样。这意味着每个对象都有权设置人名。

答案 2 :(得分:1)

除了扩展之外,protected的用途可以用于管理类。

请参阅,protected并不意味着只有子类可以访问相关字段。但是同一个包中的任何类。

假设您有abstract class Entity

另一个class SpecificEntity1 extends Entity

另一个class SpecificEntity2 extends Entity

但你想要一种方法来跟踪所有实体。

您所做的是为特定类protected

创建构造函数

将所有类放在同一个包中,并使用EntityManager方法在该包中创建另一个类,如createEntity。这样你只能在包外使用该类创建实体。