国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 編程 > Java > 正文

Java----Socket編程之模擬客戶端Client

2019-11-06 06:23:27
字體:
來源:轉載
供稿:網友

Socket的英文原義是“孔”或“插座”,作為BSD UNIX的進程通信機制,取后一種意思。通常也稱作”套接字”,網絡上的兩個程序通過一個雙向的通信連接實現數據的交換,這個連接的一端稱為一個socket。 以java為例,Socket和ServerSocket類庫位于java.net包中。ServerSocket用于服務器端,Socket是建立網絡連接時使用的。在連接成功時,應用程序兩端都會產生一個Socket實例,操作這個實例,完成所需的會話。對于一個網絡連接來說,套接字是平等的,并沒有差別,不因為在服務器端或在客戶端而產生不同級別。不管是Socket還是ServerSocket它們的工作都是通過SocketImpl類及其子類完成的。

1.Socket類的構造

Socket的構造方法有以下幾種重載形式:

Socket() Socket(InetAddress address, int port)Socket(InetAddress address, int port, InetAddress localAddr, int localPort) Socket(String host, int port)Socket(String host, int port, InetAddress localAddr, int localPort)

除了第一個不帶參數的構造方法以外, 其他構造方法都會試圖建立與服務器的連接, 如果連接成功, 就返回 Socket對象; 如果因為某些原因連接失敗, 就會拋出IOException .

//使用無參數構造方法, 設定等待建立連接的超時時間 Socket socket = new Socket();SocketAddress remoteAddr = new InetSocketAddress(192.168.0.1,9000);socket.connect(remoteAddr, 60000); //等待建立連接的超時時間為1分鐘//使用服務端ip端口的構造方法socket = new Socket(192.168.0.1, 9000);socket.setSoTimeout(60000);//等待建立連接的超時時間為1分鐘//使用對端參數,同時設置客戶端的參數信息InetAddress localAddr = InetAddress.getByName("192.168.0.2");//獲取本地IP對應的InetAddressSocket socket1 = new Socket(192.168.0.1, 9000, localAddr1, 9012);//設置本地端口為9012

Socket 類提供了3 個狀態測試方法.

isClosed(): 如果Socket已經連接到遠程主機, 并且還沒有關閉, 則返回true , 否則返回false . isConnected(): 如果Socket曾經連接到遠程主機, 則返回true , 否則返回false . isBound(): 如果Socket已經與一個本地端口綁定, 則返回true , 否則返回false .

2.Socket的選項參數設置

Socket 有以下幾個選項: TCP_NODELAY: 表示立即發送數據. SO_RESUSEADDR: 表示是否允許重用Socket 所綁定的本地地址. SO_TIMEOUT: 表示接收數據時的等待超時數據. SO_LINGER: 表示當執行Socket 的 close()方法時, 是否立即關閉底層的Socket. SO_SNFBUF: 表示發送數據的緩沖區的大小. SO_RCVBUF: 表示接收數據的緩沖區的大小. SO_KEEPALIVE: 表示對于長時間處于空閑狀態的Socket , 是否要自動把它關閉. OOBINLINE: 表示是否支持發送一個字節的TCP 緊急數據. 這些具體用法將專門寫一篇文章來介紹,在此不多贅述。

3.通過Socket發送/接收數據

如果已成功建立Socket連接,我們如何向其中寫入數據呢?需要使用getOutputStream()方法來獲得輸出流,然后使用write方法寫入byte數據。

OutputStream os = socket.getOutputStream();//獲取輸出流byte[] packet = "Hello".getBytes("");//將發送數據轉換為字節os.write(packet);//向輸出流中寫入os.flush();//刷新緩沖,將緩沖區中的數據全部取出來

同樣讀取數據使用了InputStream輸入流

InputStream is = socket.getInputStream();//獲取輸入流byte[] lengthBytes = new byte[8];is.read(lengthBytes);//讀取前八位

4.關閉Socket

Socket通信會占用包括接口在內的很多資源,所以當通信結束時,及時關閉Socket 就顯得非常重要, Socket 的 close() 方法負責關閉Socket。為了確保每次通信成功與否都會關閉Socket,所以我們一般將關閉方法寫在finally塊中。 例如:

Socket socket = null;try{ socket = new Socket(192.168.0.1,8000); }catch(Exception e){ e.PRintStackTrace(); }finally{ try{ if(socket != null){ socket.close(); } }catch(Exception e){ e.printStackTrace(); } }

4.完整程序示例

import java.io.DataInputStream;import java.io.InputStream;import java.io.OutputStream;import java.net.Socket;import java.net.SocketTimeoutException;public class SocketClient { //模擬Socket客戶端 private String host; private int port; private int soTimeout; /** * @Title: send * @Description: 發送報文,用于向指定的服務端發送消息 * @param msg 發送的消息 * @param index * @return * @throws Exception */ public String send(String msg) throws Exception { //發送 Socket socket = null; String data = msg; String returnmsg = null; try { try { socket = new Socket(host, port);//建立連接 }catch(Exception e){ System.out.println("連接服務器失敗,連接ip:"+host+",端口:"+port); } socket.setSoTimeout(soTimeout); OutputStream os = socket.getOutputStream(); byte[] packet = data.getBytes("UTF-8"); os.write(packet);//發送數據 os.flush(); InputStream is = socket.getInputStream(); DataInputStream in=new DataInputStream(is); //服務端返回的數據帶有8位數據長度,先讀取前8位長度,再按照長度讀取后面內容 byte[] lengthBytes = new byte[8]; is.read(lengthBytes); String length = ""; for(int i=0;i<lengthBytes.length;i++){ char temp=(char) lengthBytes[i]; length=length+temp; } byte returnContent[] = new byte[Integer.parseInt(length)]; in.read(returnContent); returnmsg = new String(returnContent, "UTF-8"); System.out.println(returnmsg); // 讀取返回消息 }catch (Exception e) { System.out.println("處理失敗,原因:"+e.getMessage()); } finally { try { socket.close(); } catch (Exception e) { System.out.println(); } } return returnmsg; } public String getHost() { return host; } public void setHost(String host) { this.host = host; } public int getPort() { return port; } public void setPort(int port) { this.port = port; } public int getSoTimeout() { return soTimeout; } public void setSoTimeout(int soTimeout) { this.soTimeout = soTimeout; }}

參考文章: http://blog.csdn.net/semillon/article/details/7515926


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 江源县| 霍邱县| 天峨县| 泾阳县| 阿城市| 鄄城县| 昭平县| 会昌县| 德州市| 东阿县| 介休市| 深水埗区| 偏关县| 迁西县| 屯昌县| 渝中区| 萍乡市| 宁武县| 建瓯市| 囊谦县| 涞源县| 吴川市| 霸州市| 炉霍县| 尚义县| 杭锦后旗| 进贤县| 乐陵市| 临沭县| 寿宁县| 余姚市| 定远县| 茌平县| 绥化市| 泰州市| 双鸭山市| 麟游县| 灵台县| 吉首市| 四子王旗| 荔浦县|