1

Java SE 7チュートリアルのデッドロックセクションには、以下に示す例があります。mainメソッドが2つのSTATICネストされたオブジェクトを作成できる理由がわかりません(実際には、静的なネストされたクラスとして定義されています)。静的クラスのインスタンスはないと言われていますよね?誰かが私を助けることができますか?ありがとう。

================================================== =========================================アルフォンスとガストンは友達であり、偉大な信者です礼儀で。礼儀の厳格なルールは、あなたが友人に頭を下げるとき、あなたはあなたの友人が弓を返す機会を得るまであなたは頭を下げたままでなければならないということです。残念ながら、このルールでは、2人の友人が同時にお辞儀をする可能性は考慮されていません。このサンプルアプリケーションDeadlockは、この可能性をモデル化しています。

public class Deadlock {
    static class Friend {
        private final String name;
        public Friend(String name) {
            this.name = name;
        }
        public String getName() {
            return this.name;
        }
        public synchronized void bow(Friend bower) {
            System.out.format("%s: %s"
                + "  has bowed to me!%n", 
                this.name, bower.getName());
            bower.bowBack(this);
        }
        public synchronized void bowBack(Friend bower) {
            System.out.format("%s: %s"
                + " has bowed back to me!%n",
                this.name, bower.getName());
        }
    }

    public static void main(String[] args) {
        final Friend alphonse =
            new Friend("Alphonse");
        final Friend gaston =
            new Friend("Gaston");
        new Thread(new Runnable() {
            public void run() { alphonse.bow(gaston); }
        }).start();
        new Thread(new Runnable() {
            public void run() { gaston.bow(alphonse); }
        }).start();
    }
}

Deadlockが実行されると、bowBackを呼び出そうとしたときに両方のスレッドがブロックされる可能性が非常に高くなります。各スレッドは他のスレッドがボウを出るのを待っているため、どちらのブロックも終了しません。

4

2 に答える 2

1

Javaチュートリアルから:事実上、静的にネストされたクラスは、パッケージ化の便宜のために別のトップレベルクラスにネストされた動作上のトップレベルクラスです。

デッドロックの内側からフレンドを削除して、動作を変更せずに外部クラスとして使用することができます。

「静的」とは、外部クラスの変数とメソッドへのアクセスを指します。静的(クラス)メソッドと同様に、静的にネストされたクラスは、インスタンス変数またはそれを囲むクラスで定義されたメソッドを直接参照できません。オブジェクト参照を介してのみ使用できます。

「静的クラスのインスタンスがない」とはどこにも書かれていないと思います。外部クラスを静的にすることはできず、ネストされたクラスは事実上外部クラスです。

良い質問ですが、私は最近この例を調べましたが、これについては考えていませんでした。

于 2012-05-15T06:02:30.270 に答える
0

編集:スレッドの作成はメソッドの呼び出しよりもはるかに遅いですが、初めてそれらをロードするのはさらに時間がかかります。

コードがそうであるように、メソッドをロードするのにかかる時間は、ロードされるまでメソッドを呼び出すことができないため、2つのスレッドを効果的に整列させるため、これはデッドロックを引き起こします。

スレッドの開始の間に次の行を追加すると、デッドロックは発生しません。

Thread.sleep(50); 

同様に、スレッドを作成する前にメソッドを呼び出してメソッドが確実にロードされるようにすると、タイミングがスレッドの開始に依存するため、デッドロックが発生しなくなります。

alphonse.bow(gaston);

前の答え。

私見、デッドロックが発生する可能性はほとんどありません。

これらのタスクを繰り返し実行すると、最終的にデッドロックが発生します。これらの操作は、異なる時間に1回だけ実行します。これは、新しいスレッドの開始には、2つのロックが取得されるまでの時間よりもはるかに長い時間がかかるためです。(100倍以上の差)

これはおそらく100回の実行に1回デッドロックすると予想されますが、それよりも少ない頻度である可能性があります。

静的クラスのインスタンスはないと言われていますよね?

Friendのインスタンスが2つあるので、それが何を意味するのかわかりません。Deadlock

于 2012-05-15T05:59:51.907 に答える