Java Socket 循环接收数据readLine()阻塞问题解决办法

写在前面

只能说基础不牢吧,代码逻辑一切OK,就是接收不到服务器信息,发送没问题。
因为服务器不是我能控制的,只能在客户端想办法解决,后来断点知道了readLine()阻塞的情况,大无语呀,阻塞好是好,但你要换行符,我哪知道服务器给的是什么。

这里socket的连接之类的代码很多,就不重复贴了,只放些解决方案供有同样问题的朋友参考

解决方案一 加换行符

就是上面提到的readLine()要换行符才知道传送完成,所以这个只能是服务器端发送数据给客户端时,结尾一定要加个\r\n
又或者使用 println() 发送数据
如果服务器客户端都是你维护,那这个解决方案最简单高效。

以下代码当个参考,m_clientSocket 即是服务端通信用Socket,非连接用的ServerSocket

 public void SendMessage(String msg) {
     new Thread(new Runnable() {
         @Override
         public void run() {
             try {
                 if (m_clientSocket.isConnected()) {
                     if (!m_clientSocket.isOutputShutdown()) {
                         PrintWriter printWriter = new PrintWriter(new OutputStreamWriter(m_clientSocket.getOutputStream()), true);
                         printWriter.println(msg);
                     }
                 }
             } catch (IOException e) {
                 log(e.getMessage());
             }
         }
     }).start();
 }

解决方案二 使用Read() 方法

这里记得新开线程或用异步任务执行接收数据的逻辑

private void WaitForData() {
    FutureTask<Void> futureTask = new FutureTask<>(new Callable<Void>() {
        @Override
        public Void call() throws Exception {
            try {
                String charset = "GBK";
                byte[] buffer = new byte[10240];
                String msg;
                int len;
                InputStream inputStream = m_clientSocket.getInputStream();
                BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream, charset));
                while (true) {
                    if (!m_clientSocket.isInputShutdown()) {
                        len = inputStream.read(buffer);
                        if (len == -1) break;
                        msg = new String(buffer, 0, len, charset);
                        log(msg);
                        // 拿到了接收到的数据msg后面就是自己的处理逻辑了,是打印还是其他了
                    }
                }
            } catch (Exception e) {
                log(e.getMessage());
            }
            return null;
        }
    });
    new Thread(futureTask).start();
}

解决方案三 DataInputStream

这种方法好是好,但没有阻塞等待,会一直循环。(突然发现阻塞也是好东西呀)
一并贴出来供参考吧,看需要的朋友使用

private void WaitForData() {
    FutureTask<Void> futureTask = new FutureTask<>(new Callable<Void>() {
        @Override
        public Void call() throws Exception {
            int i = 0;
            while (true) {
                if (!client.isInputShutdown()) {
                    try {
                        DataInputStream inputStream = new DataInputStream(client.getInputStream());
                        byte[] buffer = new byte[inputStream.available()];
                        if(buffer.length != 0){
                            inputStream.read(buffer);
                            String msg = new String(buffer);
                            clientReceiveData.OnClientReceiveData(msg);
                        }
                        i++;
                        log(String.valueOf(i));
                    } catch (Exception ee) {
                        log(ee.getMessage());
                    }
                }
            }
        }
    });
    new Thread(futureTask).start();
}
  • 1
    点赞
  • 20
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Java中,使用Socket实现网络通信,可以很方便地创建客户端和服务器端程序。下面是一个例子,演示如何创建一个TCP服务器并接收客户端发送的消息: ```java import java.io.*; import java.net.*; public class Server { public static void main(String[] args) { try { // 创建服务器端Socket对象 ServerSocket serversocket = new ServerSocket(9999); System.out.println("Waiting for client connection..."); while (true) { // 等待客户端连接 Socket clientsocket = serversocket.accept(); System.out.println("Connected from: " + clientsocket.getRemoteSocketAddress()); // 接收客户端消息 BufferedReader in = new BufferedReader(new InputStreamReader(clientsocket.getInputStream())); String message = in.readLine(); System.out.println("Received from client: " + message); // 关闭连接 clientsocket.close(); } } catch (IOException e) { e.printStackTrace(); } } } ``` 上述代码创建了一个TCP服务器,监听本地的9999端口,当有客户端连接时,接收客户端发送的消息并打印出来,然后关闭连接。需要注意的是,在接收客户端消息时,使用了BufferedReader类的readLine方法,可以一次性读取一行文本数据。 创建TCP客户端也很简单,可以使用Socket对象的getOutputStream方法发送消息: ```java import java.io.*; import java.net.*; public class Client { public static void main(String[] args) { try { // 创建客户端Socket对象 Socket clientsocket = new Socket("localhost", 9999); // 发送消息 OutputStream out = clientsocket.getOutputStream(); String message = "Hello, server!"; out.write(message.getBytes()); // 关闭连接 clientsocket.close(); } catch (IOException e) { e.printStackTrace(); } } } ``` 上述代码创建了一个TCP客户端,并连接到本地的9999端口,向服务器发送一条消息"Hello, server!",然后关闭连接。需要注意的是,在发送消息时,使用了OutputStream类的write方法,可以将字节数组写入输出流中。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值