私はfollwing Javaの9モジュールがあります。内部型をリークするパブリックAPIのコンパイルが失敗しないのはなぜですか?
public class Api {
public static void foo(ImplDetail args) {}
}
と非エクスポートタイプ:エクスポートされたタイプでは
module com.example.a {
exports com.example.a;
}
package com.example.b.internal;
public class ImplDetail {}
エクスポートタイプが非を使用していますパブリックメソッドのメソッドパラメータ型としてエクスポートされた型。他のモジュールのクライアントは、パラメータタイプをインスタンス化できないため、foo()
メソッドを実際に呼び出せなかったので、コンパイラはこのような一貫性のないクラス構成を拒否すると仮定していました。
私の驚いたことに、このモジュールはjavacによって正常にコンパイルされています。私はnull
を渡す特別なケースを見ることができますが、私はそのようなAPI定義が不正なものだと考えていて、理想的にコンパイラによって強制されてはならないと考えています。
このようなケースを許可しない理由は何ですか?
あなたの詳細な回答ありがとう、スチュアート!輸出されていない型から輸出された型を派生させることは、私にとっても一貫していないように思えるので、(Sub'自体のために)コンパイルエラーを保証する必要があると言いました。しかし、おそらく、いくつかのコンパイル・ステップで記述した同じ問題があるでしょう。 – Gunnar
@ Gunnarこれをしばらく考えた後、プライベートクラスのサブクラスであるパブリッククラスを持つことは珍しいことではないことに気付きました。たとえば、java.langのJDKでは、 'StringBuffer'と' StringBuilder'はどちらもプライベートクラスである 'AbstractStringBuilder'のパブリックサブクラスです。内部プライベートクラスを持つ階層SB <:ASB <:Objectを持つのはちょっと奇妙ですが、実装を共有するためには完了です。ただし、ASBはAPIの型として公開されません。 –
フォローアップありがとう。個人的に、私はそのようなデザインが厄介であると感じます。タイプのユーザは、タイプIMOの完全な階層を見ることができるはずです。実装の共有については、プライベート共有クラスへの委任によって行うことができます。 – Gunnar