【问题标题】:Call Methods of an abstact class child抽象类子的调用方法
【发布时间】:2017-11-09 09:19:24
【问题描述】:

我有一个名为 Router 的类,它负责与 Retrofit 的接口。所以这里是所有核心方法。然后我有一个名为 ConfigurableRouter 的抽象类(它扩展了路由器),它允许我配置我的路由器。现在我希望我可以创建具有不同默认值的 ConfigurabelRouter 的子级(实际上它是一个抽象类)。

这是一个如何工作的示例:

Router.configure(M_Rout.class)
            .setPath("close-pi")
            .setParams(params)
            .setRequestMethod(Router.RequestMethod.POST)
            .setIsAuthRequested(true)
            .setCallback(new RequestResponse() {
                @Override
                protected void onSuccess(HashMap<String, String> responseItems) {}

                @Override
                protected void onGeneralError(int responseCode) {}

                @Override
                public void onFailure() {}
            })
           .sendRequest(getActivity());

这就是 Router.configure() 方法的工作原理:

public static ConfigurableRouter configure(Class<? extends ConfigurableRouter> aClass){
    ConfigurableRouter configurableRouter = null;
    try {
        configurableRouter = aClass.newInstance();
        //obj is a newly created object of the passed in type
    } catch (Exception ignored) { }
    return configurableRouter;
}

这是一个 ConfigurableRouter 方法的例子:

public ConfigurableRouter setParams(HashMap<Stthring, Object> params){
    super.setRouterParams(params);
    return this;
}

这是 M_Router 类:

public class M_Rout extends ConfigurableRouter {
@Override
public String setBasepath() {
    return "www.xxxxxxx.xx/";
}

@Override
public String setInDebigBasePath() {
    return "www.debugxxxxxxx.xx/";
}

@Override
public boolean isDebugging() {
    return false;
}

@Override
public RequestMethod setDefultRequestMethod() {
    return RequestMethod.POST;
}

@Override
public RequestResponse setDefultResponse() {
    return new RequestResponse() {
        @Override
        protected void onSuccess(HashMap<String, String> responseItems) {
            Log.d("RouterLog", "PigSUCSESSSpig");
        }

        @Override
        protected void onGeneralError(int responseCode) {

        }

        @Override
        public void onFailure() {

        }
    };
}

@Override
public ConfigurableRouter setAuthToken(String authToken) {
    return super.setAuthToken("tokenExample");
}

public void setIsAuthRequested(boolean b){
    // 
}
}

现在我的问题是我无法访问 M_Router 类中的非覆盖方法,例如 setIsAuthRequested(),即在第一个 sn-p 中。我不知道我该怎么做..尝试了不同的方式,但没有。我该怎么办?

【问题讨论】:

  • 如果你将它声明为父类的类型,你将被限制为父类提供的功能。
  • 是的,我知道.. 但是在一个项目中,我可以有不同的类,如 M_Router,具有所有不同的默认值,而不仅仅是一次
  • 所以不要在你的抽象方法中声明更多的方法。
  • 意思是说:所以不要将它声明为你的抽象类的类型,或者在你的抽象类中声明更多的方法
  • 是的,我明白了。那么这是唯一的解决方案吗?我还能做什么?

标签: java class abstract-class parent-child


【解决方案1】:
public abstract class Person {

  abstract void sayName();

}

有两种实现方式:

public class LoudPerson extends Person {

  void sayName() {
    System.out.println("I yell my name!!");
  }

}

public class RegularPerson extends Person {

  void sayName() {
    System.out.println("I will say my name");
  }

  void givesBusinessCard() {
    // whatever
  }

}

现在,如果你创建一个这样的方法:

public void handlePerson(Person person) {

}

你可以在上面调用sayName()方法,因为不管Person是什么类型,它总会有一个sayName()的实现

现在,假设您要传递RegularPerson 的实例,并调用givesBusinessCard(),这不会立即起作用。

  1. 即使您作为参数传递的所有参数都是 RegularPerson 类型,运行代码的 JVM 也不会(不能)知道这一点
  2. 其他人可以创建其他子类,并改变这种思路。
  3. 据 JVM 所知,它只是一个 Person,而所有 Person 提供的都是 sayName() 方法。

假设您需要能够调用 givesBusinessCard() 方法,您有 3 个选项。

  1. 改变你调用的方法。如果你需要调用givesBusinessCard(),你知道它是RegularPerson,所以你可以说:

    public void handlePerson(RegularPerson person) {

    }

  2. 更改您的抽象类,在其中添加方法,并在 LoudPerson 中提供该方法的失败或空实现

    公共抽象类人{

    abstract void sayName();

    abstract void giveBusinessCard();

    }

public class LoudPerson extends Person {

  void sayName() {
    System.out.println("I yell my name!!");
  }

void givesBusinessCard() throws UnsupportedOperationException {
  throw new UnsupportedOperationException("not needed here");
}
}

或 公共类 LoudPerson 扩展 Person {

  void sayName() {
    System.out.println("I yell my name!!");
  }

void givesBusinessCard()  {

}
}
  1. 在调用之前将您的人投给RegularPerson,但请务必进行实例检查:

public void handlePerson(Person person) {
// .. if ( 人 instanceof RegularPerson ) { RegularPerson p = (RegularPerson)person; p.givesBusinessCard(); } // .. }

【讨论】:

  • 这是一个完美的解释,谢谢。我遵循你在 cmets 中给我的建议
猜你喜欢
  • 2012-12-15
  • 1970-01-01
  • 1970-01-01
  • 2012-09-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-05-02
相关资源
最近更新 更多