問題タブ [java-bridge-method]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
java - リフレクション - Method::getGenericReturnType ジェネリックなし - 可視性
説明
Method::getGenericReturnType()がジェネリック型情報を取得できないという奇妙な問題があります。
最小化されたバージョンは次のとおりです。
出力は
ジェネリック型情報なし。これは私には奇妙に思えます。
ただし、A可視性をに変更するpublicと、正しく表示されます
質問
これがバグなのか、実際に予想される動作なのかはわかりません。それが予想される場合、その背後にある理由は何ですか?
AdoptOpenJDK の OpenJDK 15 を使用しています。
友人は次の方法でも再現できます。
- JDK ズールー 8
- OpenJDK 10、11、14 を採用
所見
私は多くの実験を行い、この問題を引き起こすAとの間の唯一の可視性の組み合わせは when isとis notであることがわかりました。他の組み合わせでも、期待どおりに機能します。だからだけBBpublicA public
- B
public、Aprotected - B
public、Apackage-visible - B
public、Aprivate
奇妙な行動を示します。
コードを別のファイルに移動したり、別のパッケージに入れたり、staticあちこちに追加または削除したりしてみましたが、何も変わりませんでした。
メソッドのソースコードも確認しました。
whereは、インスタンスの構築中に設定さgetGenericSignature()れる a に依存します。何らかの理由で上記の状況になっているようです。String signatureMethodnull
更新 1
クラスのバイトコードをチェックアウトしたところ、次の場所でこれが見つかりましたB.class:
私には、これは のように見えますがB、何らかの理由で、foo()単にメソッド呼び出しをAsに転送する別のメソッドを作成したため、foo()ジェネリック型情報がありません。
さらに、呼び出すB.getDeclaredMethods()と、実際にはメソッドが返されます。つまり、
このメソッドは継承されたメソッドを除外することになっていますが(ドキュメントから):
この Class オブジェクトによって表されるクラスまたはインターフェイスのすべての宣言されたメソッドを反映する Method オブジェクトを含む配列を返します。これには、パブリック、プロテクト、デフォルト (パッケージ) アクセス、およびプライベート メソッドが含まれますが、継承されたメソッドは除外されます。
B本当にラッパーメソッドを作成した場合、これは理にかなっています。
しかし、なぜそのようなメソッドを作成しているのでしょうか? この動作を説明する JLS セクションはありますか?