覆盖方法的Java Class.getMethods()行为 [英] Java Class.getMethods() behavior on overridden methods

查看:57
本文介绍了覆盖方法的Java Class.getMethods()行为的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Java中使用反射编写一个简单的JSON序列化程序时,我对Class.getMethods()的行为感到措手不及.如果重写方法的返回类型扩展了重写方法的返回类型,则Java Class.getMethods()会同时返回重写方法和重写方法.
因此,例如给定的接口:

 静态接口A {一个x();一个y();}静态接口B扩展了A {B x();一个y();} 

A.class.getMethods()返回预期的两个方法的数组但是 B.class.getMethods()返回3个方法的数组(对我来说,这有点反直观).3中的1与预期的 y()相对应,而其余两个与返回类型为 A 的原始 x()相对应,而分别是返回类型为 B x()的替代版本.这让我有些奇怪,但是数组中原始的 x()不能从任何地方访问,这使我感到有些奇怪.无论如何,我的问题是:
是否有一种简单的方法来获取类方法的仅最特殊版本的列表,而无需借助手动检查覆盖的方法并将其过滤掉?

解决方案

我的理解是,如果您过滤掉 isBridge()返回 true 的方法,则不需要方法应该消失.

这是Java如何实现协变量返回类型的伪像(桥方法也用于泛型,但这似乎与您的用例无关).

编辑有趣的是,虽然这适用于类,但似乎不适用于接口. B 的所有三种方法都标记为非桥接和非合成方法.但是,如果我创建一个实现 B 的非抽象类 C ,则其 A x()被标记为桥接和合成.

While writing a simple JSON serialiser using reflection in Java I was caught off guard by the behavior of Class.getMethods(). It appears that Java Class.getMethods() returns both overriding and overridden methods if the return type of the overriding method extends that of the overridden method.
So for example given the interfaces:

static interface A {
  A x();
  A y();
}
static interface B extends A {
  B x();
  A y();
}

A.class.getMethods() returns and array of two methods as expected however B.class.getMethods() returns an array of 3 methods (which to me was a little counter intuitive). Of the 3, 1 corresponds to the y() as expected but the remaining two correspond to the original x() with return type A and the overriding version of x() with return type B respectively. This struck me as a little odd to have but the original x() in the array since its not accessible from anywhere. Anyway my question is this:
Is there and easy way to get a list of only the most specialised versions of a class's methods without resorting to manually checking for overridden methods and filtering them out?

解决方案

My understanding is that if you filter out methods for which isBridge() returns true, the unwanted method should go away.

It is an artefact of how Java implements covariant return types (bridge methods are also used for generics, but that doesn't appear relevant to your use case).

edit Interestingly enough, while this works for classes, it doesn't seem to work for interfaces. All three methods of B are marked as non-bridge and non-synthetic. However, if I create a non-abstract class C implementing B, its A x() is marked as both bridge and synthetic.

这篇关于覆盖方法的Java Class.getMethods()行为的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆