java socket 编程学习资料收集

Socket是网络上运行的两个程序间双向通讯的一端,它既可以接受请求,也可以发送请求,利用它可以较为方便的编写网络上的数据的传递。在java中,有专门的socket类来处理用户的请求和响应。利用SOCKET类的方法,就可以实现两台计算机之间的通讯。这里就介绍一下在JAVA中如何利用socket进行网络编程。

所谓socket通常也称作"套接字",用于描述IP地址和端口,是一个通信链的句柄。应用程序通常通过"套接字"向网络发出请求或者应答网络请求。

操作java socket时用到的最多的三个方法为:

accept():主要用于服务器端产生“阻塞”,等待客户端的链接请求,并且返回一个客户端的Socket实例;

getInputStream():方法主要用来获得网络连接输入,同时返回一个InputStream对象实例;

getOutputStream():方法和上面的getInputStream相反。

一般要建立Java的Socket连接,应首先明确服务器端和客户端,服务器端使用ServerSocket监听指定的端口,使用accept等待客户端请求,链接链接,开始会话、完成会话后,关闭链接。(注意,一般socket的关闭都应该是服务器端来进行的,后面说);客户端使用Socket对网络中的某个服务器的某个端口发出链接请求,连接成功,开始会话,会话完成,Socket关闭。

一、建立服务器类

Java中有一个专门用来建立Socket服务器的类,名叫ServerSocket,可以用服务器需要使用的端口号作为参数来创建服务器对象。

 
 
  1. ServerSocket server = new ServerSocket(9998

这条语句创建了一个服务器对象,这个服务器使用9998号端口。当一个客户端程序建立一个Socket连接,所连接的端口号为9998时,服务器对象server便响应这个连接,并且server.accept()方法会创建一个Socket对象。服务器端便可以利用这个Socket对象与客户进行通讯。

 
 
  1. Socket incoming = server.accept() 

进而得到输入流和输出流,并进行封装

 
 
  1. BufferedReader in = new BufferedReader(new InputStreamReader(incoming.getInputStream()));  
  2. PrintWriter out = new PrintWriter(incoming.getOutputStream(),true); 

随后,就可以使用in.readLine()方法得到客户端的输入,也可以使用out.println()方法向客户端发送数据。从而可以根据程序的需要对客户端的不同请求进行回应。

在所有通讯结束以后应该关闭这两个数据流,关闭的顺序是先关闭输出流,再关闭输入流,即使用:

 
 
  1. out.close();  
  2. in.close(); 

二、建立客户端代码

相比服务器端,客户端要简单一些,客户端只需用服务器所在机器的ip以及服务器的端口作为参数创建一个Socket对象。得到这个对象后,就可以用"建立服务器"部分介绍的方法实现数据的输入和输出。

 
 
  1. Socket socket = new Socket("168.160.12.42",9998);  
  2. in = new BufferedReader(new InputStreamReader(socket.getInputStream()));  
  3. out = new PrintWriter(socket.getOutputStream(),true); 

以上的程序代码建立了一个Socket对象,这个对象连接到ip地址为168.160.12.42的主机上、端口为9998的服务器对象。并且建立了输入流和输出流,分别对应服务器的输出和客户端的写入。

三、建立用户界面

读者可以根据自己的喜好建立自己的用户界面,这不是本文的重点。

经过以上三个步骤,就可以建立一个比较简单的对话程序。但是,为了使这个程序更加完善,应进行以下几个改进:

一、现在服务器只能服务一个客户,也就是单线程的。可以将它改进为多线程服务器。

 
 
  1. try   
  2. { file://建立服务器    
  3.  ServerSocket server = new ServerSocket(9998);    
  4.  int i=1;    
  5.  for(;;)    
  6.  {    
  7. Socket incoming = server.accept();    
  8. new ServerThread(incoming,i).start();    
  9. i++;    
  10.  }    
  11. }catch (IOException ex){ ex.printStackTrace(); }   

循环检测是否有客户连接到服务器上,如果有,则创建一个线程来服务这个客户,这个线程的名称是ServerThread,这个类扩展了Thread类,它的编写方法与前述的服务器的写法相同。

二、为了可以随时得到对方传送过来的消息,可以在服务器以及客户端各建立一个独立的线程来察看输入流,如果输入流中有输入,则可以即时显示出来。代码如下:

 
 
  1. new Thread()  
  2. {  
  3.  public void run()  
  4.  {  
  5. try 
  6. {   
  7.  while(true)  
  8.  {  
  9. checkInput();  
  10. sleep(1000);//每1000毫秒检测一次  
  11.  }  
  12. }catch (InterruptedException ex)  
  13.  {  
  14.  }catch(IOException ex)  
  15.  {  
  16. }  
  17.  }  
  18. }.start(); 

其中的checkInput()方法为:

 
 
  1. private void checkInput() throws IOException  
  2. {  
  3.  String line;  
  4.  if((line=in.readLine())!=null) file://检测输入流中是否有新的数据  
  5. t.setPartner(line); file://将数据流中的消息显示出来  
  6. }  

运行效果:

===============================================================

服务器端代码:

复制代码
  1 package com.b510.socket1706.gui.freeechatroom;
  2 
  3 import java.io.*;
  4 import java.net.*;
  5 import java.awt.*;
  6 import java.awt.event.*;
  7 
  8 /**
  9  * 服务器端程序
 10  * 
 11  * @author Hongten
 12  * 
 13  * @time 2012-4-29 2012
 14  */
 15 public class TestServer {
 16     private ServerSocket ss;
 17     private Socket s;
 18     private DataInputStream dis;
 19     private DataOutputStream dos;
 20     private TextArea ta;
 21     private TextField tf;
 22 
 23     public static void main(String args[]) {
 24         TestServer ts = new TestServer();
 25         ts.createUI();
 26         ts.connect();
 27         ts.createThread();
 28     }
 29 
 30     public void connect() {
 31         try {
 32             ss = new ServerSocket(8888);
 33             s = ss.accept();
 34             dis = new DataInputStream(s.getInputStream());
 35             dos = new DataOutputStream(s.getOutputStream());
 36         } catch (IOException e) {
 37             e.printStackTrace();
 38             // 13701303436
 39 
 40         }
 41     }
 42 
 43     public void createUI() {
 44         Frame f = new Frame("Server");
 45         ta = new TextArea();
 46         tf = new TextField();
 47         Button send = new Button("send");
 48         Panel p = new Panel();
 49         p.setLayout(new BorderLayout());
 50         p.add(tf, "Center");
 51         p.add(send, "East");
 52         f.add(ta, "Center");
 53         f.add(p, "South");
 54         MyServerListener listener = new MyServerListener(this);
 55         send.addActionListener(listener);
 56         tf.addActionListener(listener);
 57         f.addWindowListener(new WindowAdapter() {
 58             public void windowClosing(WindowEvent e) {
 59                 System.exit(0);
 60             }
 61         });
 62         f.setSize(400, 400);
 63         f.setVisible(true);
 64     }
 65 
 66     public void createThread() {
 67         MyServerReader reader = new MyServerReader(this);
 68         reader.start();
 69     }
 70 
 71     public void close() {
 72         try {
 73             dis.close();
 74             dos.close();
 75             s.close();
 76             ss.close();
 77         } catch (IOException e) {
 78             e.printStackTrace();
 79         }
 80     }
 81 
 82     public DataInputStream getDataInputStream() {
 83         return dis;
 84     }
 85 
 86     public DataOutputStream getDataOutputStream() {
 87         return dos;
 88     }
 89 
 90     public TextArea getTextArea() {
 91         return ta;
 92     }
 93 
 94     public TextField getTextField() {
 95         return tf;
 96     }
 97 }
 98 
 99 class MyServerListener implements ActionListener {
100     private TestServer server;
101 
102     public MyServerListener(TestServer server) {
103         this.server = server;
104     }
105 
106     public void actionPerformed(ActionEvent e) {
107         TextField tf = server.getTextField();
108         String info = tf.getText();
109         server.getTextArea().append("自己说: " + info + "\n");
110         try {
111             server.getDataOutputStream().writeUTF(info);
112         } catch (IOException e1) {
113             e1.printStackTrace();
114         }
115         if (info.equals("bye")) {
116             server.close();
117             System.exit(0);
118         }
119         tf.setText("");
120         tf.requestFocus();
121     }
122 }
123 
124 class MyServerReader extends Thread {
125     private TestServer server;
126 
127     public MyServerReader(TestServer server) {
128         this.server = server;
129     }
130 
131     public void run() {
132         String info;
133         DataInputStream dis = server.getDataInputStream();
134         TextArea ta = server.getTextArea();
135         try {
136             while (true) {
137                 info = dis.readUTF();
138                 ta.append("对方说: " + info + "\n");
139                 if (info.equals("bye")) {
140                     server.close();
141                     System.exit(0);
142                 }
143             }
144         } catch (IOException e) {
145             e.printStackTrace();
146         }
147     }
148 }
复制代码

客户端代码:

复制代码
  1 package com.b510.socket1706.gui.freeechatroom;
  2 
  3 import java.io.*;
  4 import java.net.*;
  5 import java.awt.*;
  6 import java.awt.event.*;
  7 /**
  8  * 客户端程序
  9  * @author Hongten
 10  *
 11  * @time 2012-4-29  2012
 12  */
 13 public class TestClient {
 14     private Socket s;
 15     private DataInputStream dis;
 16     private DataOutputStream dos;
 17     private TextArea ta;
 18     private TextField tf;
 19 
 20     public static void main(String args[]) {
 21         TestClient tc = new TestClient();
 22         tc.createUI();
 23         tc.connect();
 24         tc.createThread();
 25     }
 26 
 27     public void connect() {
 28         try {
 29             s = new Socket("127.0.0.1", 8888);
 30             dos = new DataOutputStream(s.getOutputStream());
 31             dis = new DataInputStream(s.getInputStream());
 32         } catch (IOException e) {
 33             e.printStackTrace();
 34         }
 35     }
 36 
 37     public void createUI() {
 38         Frame f = new Frame("Client");
 39         ta = new TextArea();
 40         tf = new TextField();
 41         Button send = new Button("send");
 42         Panel p = new Panel();
 43         p.setLayout(new BorderLayout());
 44         p.add(tf, "Center");
 45         p.add(send, "East");
 46         f.add(ta, "Center");
 47         f.add(p, "South");
 48         MyClientListener listener = new MyClientListener(this);
 49         send.addActionListener(listener);
 50         tf.addActionListener(listener);
 51         f.addWindowListener(new WindowAdapter() {
 52             public void windowClosing(WindowEvent e) {
 53                 System.exit(0);
 54             }
 55         });
 56         f.setSize(400, 400);
 57         f.setLocation(600, 0);
 58         f.setVisible(true);
 59     }
 60 
 61     public void createThread() {
 62         MyClientReader reader = new MyClientReader(this);
 63         reader.start();
 64     }
 65 
 66     public void close() {
 67         try {
 68             dis.close();
 69             dos.close();
 70             s.close();
 71         } catch (IOException e) {
 72             e.printStackTrace();
 73         }
 74     }
 75 
 76     public DataInputStream getDataInputStream() {
 77         return dis;
 78     }
 79 
 80     public DataOutputStream getDataOutputStream() {
 81         return dos;
 82     }
 83 
 84     public TextArea getTextArea() {
 85         return ta;
 86     }
 87 
 88     public TextField getTextField() {
 89         return tf;
 90     }
 91 }
 92 
 93 class MyClientListener implements ActionListener {
 94 
 95     private TestClient client;
 96 
 97     public MyClientListener(TestClient client) {
 98         this.client = client;
 99     }
100 
101     public void actionPerformed(ActionEvent e) {
102         TextField tf = client.getTextField();
103         String info = tf.getText();
104         client.getTextArea().append("自己说: " + info + "\n");
105         try {
106             client.getDataOutputStream().writeUTF(info);
107         } catch (IOException e1) {
108             e1.printStackTrace();
109         }
110         if (info.equals("bye")) {
111             client.close();
112             System.exit(0);
113         }
114         tf.setText("");
115         tf.requestFocus();
116     }
117 }
118 
119 class MyClientReader extends Thread {
120     private TestClient client;
121 
122     public MyClientReader(TestClient client) {
123         this.client = client;
124     }
125 
126     public void run() {
127         String info;
128         DataInputStream dis = client.getDataInputStream();
129         TextArea ta = client.getTextArea();
130         try {
131             while (true) {
132                 info = dis.readUTF();
133                 ta.append("对方说: " + info + "\n");
134                 if (info.equals("bye")) {
135                     client.close();
136                     System.exit(0);
137                 }
138             }
139         } catch (IOException e) {
140             e.printStackTrace();
141         }
142     }
143 }

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值