3

匿名内部クラスを関数に渡すと、次のように、そのクラスのメソッド内から現在のスコープ内の変数を参照できます。

class Caller {
    private Object callerPrivate;

    // ...

    public void someMethod() {
        final String callerLocal = "Eyes only";

        ISomeInterface anon = new ISomeInterface() {
                                     public void doSomethingInterfacy {
                                         System.out.println(callerPrivate.toString());
                                         System.out.println(callerLocal);
                                     }
                                  };
        // this is some other object that puts ISomeInterfaces in a queue
        // and makes them doSomethingInterfacy later
        myCallManager.enqueue(anon);
    }
}

さて、上記の someMethod が実行された後、Caller と小さな anons を持つキューは別々の道を進むことができます。私が理解している限り、JVM はすべての参照をまっすぐに保ち、これが常に機能するようにします。

しかし、たとえば、キュ​​ーがシリアル化され、プログラムがシャットダウンされて再起動された後、キューが逆シリアル化され、その中のアイテムが実行され、Caller インスタンスがなくなって忘れ去られた場合はどうなるでしょうか?

また、anon クラス内の呼び出しが機能しなくなる方法で、周囲のオブジェクトと匿名の内部クラスを分離する他の方法はありますか?

4

2 に答える 2

6

(a) ドキュメントにそう書かれており、(b) シリアル表現が安定していない (最初から安定した名前がない) ため、ローカル クラスをシリアル化しないでください。

インスタンスに外側の this および used final ローカルのフィールドを保持させたくない場合は、(静的) ネストされたクラスまたは外側のクラスを使用します。(Java) シリアル化の場合writeReplace、シリアル プロキシ オブジェクトをシリアル化するために使用できます。

于 2009-03-23T11:31:50.867 に答える
2

匿名の内部クラスに暗黙のthis参照が含まれていることを忘れないでください。つまり、周囲のクラスへの参照です。

したがって、内部クラスをシリアル化すると、外部クラスへの参照が存在します。XStreamを使用してシリアライズし、XML 出力を表示すると、これが明確にわかります。

于 2009-03-23T11:32:25.357 に答える