簡體   English   中英

Java while(true)循環只在線程內執行一次

[英]Java while(true) loop executes only once inside thread

我試圖用Java實現一個簡單的客戶端 - 服務器應用程序。

這是代碼:

Client.java

public class Client implements Runnable {
    private String hostName;
    private int portNumber;
    private String message;

    private Socket socket;
    private PrintWriter writer;
    private BufferedReader reader;

    public Client(String hostName, int portNumber, String message) {
        this.hostName = hostName;
        this.portNumber = portNumber;
        this.message = message;
    }

    public void connect() {
        try {
            socket = new Socket(hostName, portNumber);
            writer = new PrintWriter(socket.getOutputStream(), true);
            reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));

            writer.println(message);
        } catch (UnknownHostException e) {
            System.err.println("Could not resolve the host name '" + hostName + "'.");
        } catch (IOException e) {
            System.err.println("Could not get the I/O for the connection to '" + hostName + "'.");
        }
    }

    private void listenForMessages() {
        while (true) {
            try {
                System.out.println("In loop!");
                String line;
                while ((line = reader.readLine()) != null) {
                    System.out.println(line);
                }
            } catch (IOException e) {
                System.err.println(e.getMessage());
            }
        }
    }

    public void run() {
        connect();
        listenForMessages();
    }
}

Server.java

public class Server implements Runnable {
    private int portNumber;
    private String message;

    private ServerSocket serverSocket;
    private Socket clientSocket;
    private PrintWriter writer;
    private BufferedReader reader;

    public Server(int portNumber, String message) {
        this.portNumber = portNumber;
        this.message = message;
    }

    private void listen() {
        try {
            serverSocket = new ServerSocket(portNumber);
        } catch (IOException e) {
            System.err.println(e.getMessage());
        }

        while (true) {
            try {
                clientSocket = serverSocket.accept();
                writer = new PrintWriter(clientSocket.getOutputStream(), true);
                reader = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));

                String line;
                while ((line = reader.readLine()) != null) {
                    System.out.println(line);
                }

                writer.println(message);
            } catch (IOException e) {
                System.err.println(e.getMessage());
                break;
            }
        }
    }

    public void run() {
        listen();
    }
}

這是主要的課程:

public class Test {
    public static void main(String[] args) {
        Client client = new Client("localhost", 4444, "Hello from client!");
        Server server = new Server(4444, "Hello from server!");

        Thread serverThread = new Thread(server);
        serverThread.start();

        Thread clientThread = new Thread(client);
        clientThread.start();
    }
}

代碼的邏輯很簡單:客戶端和服務器都在等待while(true)循環內的消息。

服務器的listen方法中的while循環執行得很好。 但是,在listenForMessages方法中,循環似乎只執行一次。 我只在屏幕上看到一個“In loop”。

你能弄明白問題是什么嗎?

先感謝您!

但是,在listenForMessages方法中,循環似乎只執行一次。 我只在屏幕上看到一個“In loop”。

實際上並不是因為循環只執行一次,因為reader.readLine()會使當前線程等到它收到整行,如果你檢查Server的代碼,它會先讀取並讀取一個無限循環,因為reader.readLine()只會在流的末尾返回null ,所以在這種情況下套接字將被關閉。

如果你想在客戶端和服務器之間實現某種乒乓,只需讀取然后寫入一邊寫入和讀取,另一邊寫為下一個:

Client代碼:

public void connect() {
    try {
        socket = new Socket(hostName, portNumber);
        writer = new PrintWriter(socket.getOutputStream(), true);
        reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));

    } catch (UnknownHostException e) {
        System.err.println("Could not resolve the host name '" + hostName + "'.");
    } catch (IOException e) {
        System.err.println(
            "Could not get the I/O for the connection to '" + hostName + "'."
        );
    }
}

private void listenForMessages() {
    while (true) {
        try {
            System.out.println("In loop!");
            // Write the message for the server
            writer.println(message);
            // Read the message from the server
            System.out.println(reader.readLine());
        } catch (IOException e) {
            System.err.println(e.getMessage());
        }
    }
}

Server代碼:

while (true) {
    try {
        clientSocket = serverSocket.accept();
        writer = new PrintWriter(clientSocket.getOutputStream(), true);
        reader = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));

        while (true) {
            // Read the message from the client
            System.out.println(reader.readLine());
            // Write the message for the client
            writer.println(message);
        }


    } catch (IOException e) {
        System.err.println(e.getMessage());
        break;
    }
}

輸出:

In loop!
Hello from client!
Hello from server!
In loop!
Hello from client!
Hello from server!
...

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM