4

この質問は、過去にさまざまな形で尋ねられたことは間違いありませんが、特定のシナリオについてはそれほど多くはありません。

UDP経由でネットワークメッセージを受信するのを待っている間にブロックしているスレッドを停止する最も正しい方法は何ですか.

たとえば、次のスレッドがあるとします。

public class ClientDiscoveryEngine extends Thread {

    private final int PORT;

    public ClientDiscoveryEngine(final int portNumber) {
        PORT = portNumber;
    }

    @Override
    public void run() {
        try {
            socket = new DatagramSocket(RECEIVE_PORT);

            while (true) {
                final byte[] data = new byte[256];
                final DatagramPacket packet = new DatagramPacket(data, data.length);

                socket.receive(packet);
            }
        } catch (SocketException e) {
            // do stuff 1
        } catch (IOException e) {
            // do stuff 2
        }
    }
}

さて、より正しい方法はinterrupt()メソッドを使用することでしょうか? たとえば、次のメソッドを追加します。

@Override
public void interrupt() {
    super.interrupt();
    // flip some state?
}

私の唯一の懸念は、socket.receive()割り込み不可能なブロッキング方法ではないということですか? 私が考えた1つの方法は、そのメソッド呼び出しで上記のように割り込みメソッドを実装socket.close()runSocketException. while(true)または、割り込みメソッドで反転する状態を使用する代わりに。これが最善の方法ですか?それとももっとエレガントな方法がありますか?

ありがとう

4

4 に答える 4

4

receiveメソッドは中断できないようです。ソケットを閉じることができます:javadocによると:

このソケットで現在ブロックされているスレッドはreceive(java.net.DatagramPacket)、SocketExceptionをスローします

setSoTimeoutまた、受信メソッドを短時間だけブロックするために使用することもできます。メソッドが戻った後、スレッドはメソッドが中断されているかどうかを確認し、この短い時間の間、受信を再試行できます。

于 2011-08-20T14:26:47.997 に答える
3

この回答を読んでくださいブロッキングアクションを待機しているスレッドを中断しますか?

于 2011-08-20T14:18:33.427 に答える
2

スレッドを停止するには、Javaで割り込みも停止も使用しないでください。質問の最後で提案したように、最良の方法は、必要に応じて立ち上がることができるフラグによって制御されるmainメソッド内のループを作成することです。

これに関する古いリンクは次のとおりです:http: //download.oracle.com/javase/1.4.2/docs/guide/misc/threadPrimitiveDeprecation.html

スレッドを停止する他の方法は非推奨であり、これほど多くの制御を提供しません。また、これはエグゼキュータサービスによって少し変わった可能性があります。私はまだそれについて多くを学ぶ時間がありませんでした。

また、スレッドが何らかのIO状態でブロックされてソケットを待機するのを回避したい場合は、ソケットに接続と読み取りタイムアウトを与える必要があります(メソッドsetSoTimeout)。

よろしく、ステファン

于 2011-08-20T14:25:53.903 に答える
0

これは簡単なものの 1 つです。UDP ソケットでブロックされている場合は、受信スレッドに「停止」するように指示する UDP メッセージをソケットに送信します。

Rgds、マーティン

于 2011-08-21T00:52:56.797 に答える