我在Java中有抽象类。我想用反射来调用他的子类的特定方法(如果它存在)。
public abstract class Parent {
public void doIt(String functionName) {
if (the caller class have method called as functionName parameter) {
call it
}
}
}
public class Child extends Parent{
public void spacialMethod() {
System.out.println("Child special method called");
}
}
public class Child2 extends Parent{
// Empty
}
所以,如果我将运行该代码:
Child child = new Child();
child.doIt("spacialMethod"); // Will print the text
Child2 child2 = new Child2();
child2.doIt("spacialMethod"); // Nothing will happened
如果当前子类具有名为“specialMethod”的方法,我如何检查父类?
答案 0 :(得分:5)
可能做你所要求的事情(见答案的结尾),但如果没有充分理由的话,设计很差。
如果您不需要在运行时确定名称,我会在Parent
中将方法定义为什么都不做,然后调用它;如果子类重写它,那很好。
public abstract class Parent {
public void doIt() {
this.specialMethod();
}
public void spacialMethod() {
// Do nothing
}
}
public class Child extends Parent{
@Override
public void spacialMethod() {
// Optionally call super.specialMethod() here
System.out.println("Child special method called");
}
}
public class Child2 extends Parent{
// Empty
}
但是如果你真的希望用反射来做(例如,你需要在运行时定义名称),那就不难了:
// Not recommended if you can avoid it
public void doIt() {
try {
this.getClass().getMethod("specialMethod").invoke(this);
}
catch (/*...appropriate exception handling...*/) {
}
}
答案 1 :(得分:0)
除了TJ Crowder的答案,您可以使用getDeclaredMethods
获取所有方法并调用特殊。
public void doIt() {
Method[] methods = getClass().getDeclaredMethods();
for(Method method : methods){
if(method.getName().contains("special"){
method.invoke(this);
}
}
}
答案 2 :(得分:0)
只是一个没有反思的例子:
有一种专门为每个子类实现或未实现的“访问者”;实施时,它会委托给孩子所需的方法。
请注意,与下面的示例不同,访问者实现可以在类本身外部,因此孩子甚至不必知道它将如何被访问。
public interface SpecialOpAccessor {
void doIt();
}
public abstract class Parent {
protected SpecialOpAccessor accessor;
public void doIt() {
if ( accessor != null ) {
accessor.doIt();
}
}
}
public class Child extends Parent{
public Child() {
super();
this.accessor = new SpecialOpAccessor() {
@Override
public void doIt() {
Child.this.spacialMethod();
}
}
}
public void spacialMethod() {
System.out.println("Child special method called");
}
}
public class Child2 extends Parent{
public Child() {
super();
this.accessor = null;
}
}