Java socket通信,多对多自由随意通信实例

本文介绍了一种Java Socket通信方式,允许客户端和服务器端自由、随意地进行多对多通信,避免了传统实现中可能出现的线程阻塞问题。通过使用DataInputStream和DataOutputStream替换InputStreamReader和OutputStreamReader,确保了通信的连续性。

在这里,先澄清一下,我这里说的是一个客户端一个服务器端通信,但是它们可以自由说话,就像聊QQ一样,但是我百度到网上大多例子很多都只能客户端说一句话,服务器说一句话,这样肯定不是我们所需要的,今天为大家带来的是可以随意说话。
像这样,大家可以很容易的就想到需要多线程来处理,两个线程,一个控制socket传过来的数据,一个处理,传过去的数据,但是在传过去的时候,由于需要键盘输入,非常容易导致线程阻塞,不能继续运行,导致只能你说一句,然后我说一句。这里我把传统的InputStreamReader和OutputStreamReader改为DataInputStreamReader和DataOutputStreamReader,这样就不会导致线程阻塞了。
大概就是这样的。

         InputStream is = s1.getInputStream();  //s1是socket引用
          DataInputStream dis = new DataInputStream(is);   //用dataInputStream包装一下然后就不会产生线程阻塞
          //实例化输出流
          OutputStream os = s1.getOutputStream();
          DataOutputStream dos = new DataOutputStream(os);

下面给出代码:
客户端的代码:

import java.io.*;
import java.net.*;

public class EchoClient{
  public static void main(String[] args){
    new EchoClient();
}
  public EchoClient() {
      try{
          //链接sever端
          Socket s1 = new Socket("localhost",8888);
          //实例化输入流
          InputStream is = s1.getInputStream();
          DataInputStream dis = new DataInputStream(is);   //用dataInputStream包装一下然后就不会产生线程阻塞
          //实例化输出流
          OutputStream os = s1.getOutputStream();
          DataOutputStream dos = new DataOutputStream(os);
          //实例化并启动两个进程
          new MyClientReader(dis).start();
          new MyClientWriter(dos).start();
          //捕获异常
        }catch(SocketException e){
          e.printStackTrace();
        }catch(IOException e){
            e.printStackTrace();
        }  
      }
 }




//创建一个进程用来进行接收读取数据
class MyClientReader extends Thread{
  private DataInputStream dis;
  public MyClientReader(DataInputStream dis){
    this.dis = dis;
  }
  @Override
  public void run(){
    String msg;
    try{
      while(true){
      msg = dis.readUTF();   
      System.out.println("对方说:"+msg);
      if(msg.equals("bye")){
        System.out.println("服务器下线,程序退出");
        System.exit(0);
      }
    }
    }catch(IOException e){
      System.out.println(e);
    }
  }
}
//创建一个进程用来写入并发送数据
class MyClientWriter extends Thread{
  private DataOutputStream dos;
  public MyClientWriter(DataOutputStream dos){
    this.dos = dos;
  }
  @Override
  public void run(){
    InputStreamReader isr = new InputStreamReader(System.in);
    BufferedReader br = new BufferedReader(isr);
    String msg;
    try{
    while(true){
      msg = br.readLine();
      dos.writeUTF(msg);
      if(msg.equals("bye")){
        System.out.println("客户端下线,程序退出");
        System.exit(0);
      }
    }
    }catch(IOException e){
      System.out.println(e);
    }
  }
}

服务器端代码:

import java.io.*;
import java.net.*;

public class EchoServer{
  public static void main(String[] args){
    new EchoServer();
}
  public EchoServer() {
      try{
          //设置sever端的链接
          ServerSocket s = new ServerSocket(8888);
          System.out.println("服务器启动");
          Socket s1 = s.accept();//sever等待链接
          System.out.println("客户端连接===== " 
                  +s1.getInetAddress() + ":" +s1.getPort());

          //实例化输出流
          OutputStream os = s1.getOutputStream();
          DataOutputStream dos = new DataOutputStream(os);
          //实例化输入流
          InputStream is = s1.getInputStream();
          DataInputStream dis = new DataInputStream(is);

          //实例化两个线程的对象并启动线程
          new Thread(new MyServerReader(dis)).start();
          new Thread(new MyServerWriter(dos)).start();
        }
        //捕获异常
        catch(SocketException e){
                e.printStackTrace();
        }catch(IOException e){
                e.printStackTrace();
        }
      }
  }


//创建一个进程用来进行接收读取数据
class MyServerReader implements Runnable{
  private DataInputStream dis;
  public MyServerReader (DataInputStream dis){
    this.dis = dis;
  }
  public void run(){
    String msg;
    try{
      while(true){
        msg = dis.readUTF();
        System.out.println("对方说:" + msg);
        if(msg.equals("bye")){
          System.out.println("客户端下线,程序退出");
          System.exit(0);
        }
      }
    }catch(IOException e){
      System.out.println(e);
    }
  }
}
//创建一个进程用来写入并发送数据
class MyServerWriter implements  Runnable{
  private DataOutputStream dos;
  public MyServerWriter(DataOutputStream dos){
    this.dos = dos;
  }
  public void run(){
    InputStreamReader isr = new InputStreamReader(System.in);
    BufferedReader br = new BufferedReader(isr);
    String msg;
    try{
      while(true){
        msg = br.readLine();
        dos.writeUTF(msg);
        if(msg.equals("bye")){
          System.out.println("服务器下线,程序退出");
          System.exit(0);
        }
      }
      }catch(IOException e){
      System.out.println(e);
    }
  }
}

有什么问题可以联系我。共同进步!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值