使用ServerSocket和Socke对象t建立简单的套接字(Socket)通信。
1.在C/S通信模式中, Server端需要创建监听端口的 ServerSocket,负责接收客户连接请求。
以下是通信的服务器端程序:
package Server1; import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; import java.io.PrintWriter; import java.net.ServerSocket; import java.net.Socket; public class Server1 { public static void main(String[] args) { // TODO Auto-generated method stub ServerSocket serverSocket=null; //创建一个ServerSocket对象 Socket socket=null; //创建一个socket对象 BufferedReader sockIn; PrintWriter sockOut; //创建输入输出对象 BufferedReader stdIn=new BufferedReader(new InputStreamReader(System.in)); //使用BufferedReader包裹输入流对象,获得输入字段。 try{ serverSocket=new ServerSocket(8888); //这里创建了一个端口号为8888的ServerSocket,ServerSocket是服务器Socket, //可以用来侦听连接,为每个新建立的连接都创建一个Socket对象. System.out.println("server listening on port 8888"); socket=serverSocket.accept(); //调用ServerSocket的accept()方法,会返回一个socket,保存在已经声明的socket中,这个socket就代表这次连接 if(socket==null){ //判断sockt是否为空 System.out.println("socket is null"); System.exit(1); } System.out.println("accept connection from:"+socket.getInetAddress().getHostAddress()); //socket代表这次连接,可以取IP地址 sockIn=new BufferedReader(new InputStreamReader(socket.getInputStream())); //创建输入流,可以使用这个对象接收Client发来的数据 sockOut=new PrintWriter(socket.getOutputStream()); //创建输出流,可以使用这个对象向Client发送数据 sockOut.println("hello I am server"); //使用sockOut对象发送信息 sockOut.flush(); //在使用缓冲区传输数据时,添加flush强制发送数据,不必等缓冲区慢,防止小数据无法传输 String s=sockIn.readLine(); //使用sockIn读取接收的数据 System.out.println("Server received:"+s); sockOut.close(); sockIn.close(); socket.close(); serverSocket.close(); }catch(Exception e){ System.out.println(e.toString()); System.out.println("server exit"); } } }2. socket用于建立点对点的连接,在建立连接前,必须有一方监听,一方请求,一旦建立连接后,就可以利用socket实现数据的双向传输。
以下是Client客户端的代码,为方便测试,直接使用127.0.0.1作为服务器地址。
package Client1; import java.io.BufferedReader; import java.io.InputStreamReader; import java.io.PrintWriter; import java.net.Socket; public class Client1 { public static void main(String[] args) { // TODO Auto-generated method stub Socket socket=null; BufferedReader sockIn; PrintWriter sockOut; try{ socket=new Socket("127.0.0.1",8888); //建立socket连接,连接本机地址,8888端口 if(socket==null){ //判断是否连接 System.out.println("socket null,connection error"); System.exit(1); } System.out.println("conected to server"); sockIn=new BufferedReader(new InputStreamReader(socket.getInputStream())); sockOut=new PrintWriter(socket.getOutputStream()); //创建输入输出流,这时的sockIn已经从socket中接收到数据 sockOut.println("hello,I am client"); //使用sockOut发送数据 sockOut.flush(); String s=sockIn.readLine(); System.out.println("Client recived:"+s); sockOut.close(); sockIn.close(); socket.close(); }catch(Exception e){ System.out.println(e.toString()); System.out.println("client exit"); } } }部分代码注释参见服务器端
3.socket通信的本地测试。
由于在eclipse中难以测试通信,需要使用cmd进行测试,在使用cmd测试时,需要注意运行时包的问题。
网上有说法在eclipse中 窗口->新建窗口 可以多窗口测试,本人实测无效,两个窗口公用一个控制台,无法显示预期结果(如有问题,欢迎指正)。
以作者的路径为例,我的.JAVA文件在C:\Users\lenovo\workspace\ch16\src\Client1\Client1.java
使用该地址编译是可以通过的,但是无法运行,会报错,
Exception in thread "main" java.lang.NoClassDefFoundError
如图:
这是由于包嵌套的原因,应该使用如下的关系编译,程序运行结果如图:
仅为本人学习记录,欢迎交流指正