需要解释Java中的接口和方法

时间:2015-07-10 14:47:06

标签: java

看看这段代码:

public interface Foo {
    public void bar() throws Exception;
}

public class FooImpl implements Foo {
     public void bar() {
}

public static void main(String args[]) {
    Foo foo = new FooImpl();
    foo.bar();
}

为什么我会得到一个"未处理的异常类型"编译错误,而如果我改变了

Foo foo = new FooImpl();

FooImpl foo = new FooImpl();

我不会收到任何错误?

根据我的理解,公共方法使用动态绑定,所以不应该使用原始代码调用FooImpl的bar()方法吗?

3 个答案:

答案 0 :(得分:3)

printf抛出一个已检查的异常;尽管覆盖Foo#bar,但FooImpl#bar却没有。在确定您的代码是否需要捕获异常时,bar会考虑静态类型。

答案 1 :(得分:1)

关键是你可以减少从你覆盖的方法抛出的异常列表(在接口的情况下实现)。这并不违反班级合同。

现在,当您使用对接口的引用时,编译器会看到调用的方法被声明为抛出异常,因此您必须处理它。

但是,如果您使用对实现类的引用,编译器会发现您已经减少了实现/重写方法的异常列表,因为您的实现根本不会抛出该异常,因此没有必要强迫您处理从未抛出的东西。

答案 2 :(得分:0)

您已声明Foo::bar可能会抛出已检查的异常,因此如果您的变量声明为Foo类型,那么您必须处理异常的可能性。

您已声明FooImpl::bar不会抛出已检查的异常,因此如果您的变量声明为FooImpl类型,则您不必处理异常的可能性。

多态性的一点是,如果你的变量的类型为Foo,那么调用bar的代码就不知道它所获得的方法的实现方式;它只知道Foo声明的方法。