我正在做一些阅读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中的私有方法是受保护的最终?我的子类教授可以通过基类中的构造函数访问它们。
答案 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
。这样你只能在包外使用该类创建实体。