如何通过参数类型选择重载方法?

时间:2018-12-12 13:34:18

标签: java polymorphism overloading

我正在尝试根据参数类型重载我的方法:

FieldError扩展了ObjectError

private String getMessage(final FieldError fieldError) {
    return String.format("%s %s", fieldError.getField(), fieldError.getDefaultMessage());
}

private String getMessage(final ObjectError objectError) {
    return objectError.getDefaultMessage();
}

现在,如果我有一个List<ObjectError>并为该List的元素调用上述方法,则无论{上的元素是哪种类型(ObjectErrorFieldError) {1}}是,总是会调用
getMessage(final ObjectError objectError)

enter image description here

List

为什么会这样?如果这只是它的工作方式,是否有可能不使用List<ObjectError> errors; getMessage(errors.get(0)); if

2 个答案:

答案 0 :(得分:6)

仅当编译时类型已知时,方法重载解析在编译时执行。因此,传递给方法调用的参数的编译时类型决定了选择哪个重载方法。

由于您将List<ObjectError>的元素传递给方法调用,因此始终选择String getMessage(final ObjectError objectError),并且存储在该List中的实例的运行时类型没有区别

解决问题的一种方法是将getMessage()方法移至ObjectError类,并在FieldError子类中覆盖它。

代替

getMessage(errors.get(0))

您会打电话

errors.get(0).getMessage()

这将起作用,因为方法重写是在运行时解决的。

答案 1 :(得分:1)

errors是一个列表,所以errors.get(0)是一个ObjectError。 据此,使用带ObjectError的方法是因为它是在编译时而不是在运行时链接的。

为了执行所需的操作,应在ObjectError类中添加一个getMessage()方法,并为FieldError覆盖它。然后,您真的使用了多态性:

public class ObjectError {
  [...]
  public void getMessage() {
    return this.getDefaultMessage();
  }
  [...]
}

public class FieldError {
  [...]
  @Override
  public void getMessage() {
    return String.format("%s %s", this.getField(), this.getDefaultMessage());
  }
  [...]
}