pit*_*las 5 java oop inheritance
看一下这段代码(从这里开始)
abstract class EntityA {
AssocA myA;
abstract void meet();
}
abstract class AssocA {
int something;
abstract void greet();
}
class AssocAConcrete extends AssocA {
void greet() {
System.out.println("hello");
}
void salute() {
System.out.println("I am saluting.")
}
}
class EntityAConcrete extends EntityA {
void meet() {
System.out.println("I am about to meet someone");
((AssocAConcrete)myA).salute();
}
}
Run Code Online (Sandbox Code Playgroud)
对于父类和关联类,有两个并行的继承树.问题在于第23行:
((AssocAConcrete)myA).salute();
这是一种痛苦,我的代码中都有这种东西.尽管该行是Entity具体实现的一部分,但我需要提醒一下,我想使用AssocA,AssocAConcrete的具体实现.
是否有某种注释来声明这种关系?或者是否有更好的,更通俗的Java方式来表达这种设计?谢谢!
这是对@Dave的回应,因为我想把一些代码放进......
有趣!所以调用看起来像这样:
AssocAConcrete myAssoc = new Assoca();
EnitityA<T extends AssocA> myEntity = new EntityA<AssocAConcrete>();
myEntity.setAssoc(myAssoc);
myAssoc.salute();
Run Code Online (Sandbox Code Playgroud)
是?太棒了.我想我会用它!
我认为使用泛型更加整洁......
abstract class EntityA<T extends AssocA> {
// Basically, this means myA is at least an AssocA but possibly more...
T myA;
abstract void meet();
}
abstract class AssocA {
int something;
abstract void greet();
}
class AssocAConcrete extends AssocA {
void greet() {
System.out.println("hello");
}
void salute() {
System.out.println("I am saluting.");
}
}
class EntityAConcrete extends EntityA<AssocAConcrete> {
void meet() {
System.out.println("I am about to meet someone");
myA.salute();
}
}
Run Code Online (Sandbox Code Playgroud)
除了避免强制转换外,这也使得在AssocA实现中添加不同功能变得更加容易.应该总是有一种方法可以在不使用虚拟实现(即只抛出"NotImplementedException"的方法)或强制转换的情况下执行操作.即使重构时间并不总是那么容易或值得.换句话说,没有人会因为施法而责怪你(好吧......也许有些人会,但你不能讨好每个人).
编辑(实例化注释):
来自@pitosalas的评论如下......
//Won't work...can't call 'new' on abstract class AssocA
AssocAConcrete myAssoc = new Assoca();
//Instead, do this...
AssocAConcrete myAssoc = new AssocAConcrete();
Run Code Online (Sandbox Code Playgroud)
然后....
// Again, won't work. T is only declaring the type inside your class/method.
// When using it to declare a variable, you have to say EXACTLY what you're making,
// or at least something as exact as the methods you're trying to invoke
EnitityA<T extends AssocA> myEntity = new EntityA<AssocAConcrete>();
//Instead do this...
EnitityA<AssocAConcrete> myEntity = new EntityAConcrete();
// Or this...
EntityAConcrete myEntity = new EntityAConcrete();
Run Code Online (Sandbox Code Playgroud)
然后这应该是好的......
// Assuming this is defined as `public void setAssoc(T newAssoc) {this.myA = newAssoc;}`
myEntity.setAssoc(myAssoc);
myAssoc.salute();
Run Code Online (Sandbox Code Playgroud)