Android網絡通訊Socket使用

      前一段時間作項目,涉及到TCP和UDP的使用,長期作單機的東西,一下跳到網絡真的不適應,記錄一下這些東西的入門級使用。java

      整體來講,TCP和UDP的使用流程分三步,只是TCP和UDP使用的類有所不一樣服務器

圖一 整體流程網絡

        具體使用的類在表一中列出,TCP是使用流傳輸,而UDP將數據打包發送。socket


TCP/IP UDP
Socket Scoket DatagramSocket
Outputstream DataOutputStream/PrintWirter DatagramPacket
send Outputstrem.flush(); DatagramPacket.send
        其中有些地方仍是比較困惑的:DataOutputStream/PrintWirter有什麼區別呢?

  客戶端-TCP使用方法
spa

                Socket socket = null;
		DataOutputStream out = null;
		//DataInputStream in = null;

		try {
			//Socket實例化
			socket = new Socket();
			//IP地址對象構造
			InetAddress addr = Inet4Address.getByName(ip);
			//1)Socket連接服務器(指明端口和IP)
			socket.connect(new InetSocketAddress(addr, port));
			////設置超時限制(未使用)
			// socket.setSoTimeout(2000);
			//2)獲取Socket對象的OutputStream
			out = new DataOutputStream(socket.getOutputStream());
			//in = new DataInputStream(socket.getInputStream());
			if (out != null) {
				//特殊格式(能夠忽略)
				String value = msg;
				byte[] data = value.getBytes();
				int size = data.length;

				byte[] bt = new byte[4];
				bt[0] = (byte) size;
				bt[1] = (byte) (size >> 8);
				bt[2] = (byte) (size >> 16);
				bt[3] = (byte) (size >> 24);
				//寫入數據
				out.write(bt);
				out.write(data);
				//3)傳輸數據
				out.flush();

			}
		} catch (Exception e) {
			// System.out.println(e.getMessage());
		} finally {
			try {
				if (out != null)
					out.close();
				//if (in != null)
					//in.close();
				if (socket != null)
					socket.close();
			} catch (IOException e) {
			}
		}

   客戶端-UDP使用方法code

DatagramSocket socket;
		try {
			//特殊格式(能夠忽略)
			byte[] data = msg.getBytes(charset);
			int size = data.length;

			byte[] bt = new byte[4];
			bt[0] = (byte) size;
			bt[1] = (byte) (size >> 8);
			bt[2] = (byte) (size >> 16);
			bt[3] = (byte) (size >> 24);

			//1)DatagramSocket對象實例化
			socket = new DatagramSocket();
			//IP地址對象實例化
			InetAddress ipAdress = InetAddress.getByName(ip);
			//2)構造DatagramPacket對象,用於封裝和發送數據
			DatagramPacket packet = new DatagramPacket(data, data.length,
					ipAdress, port);
			//3)數據發送
			socket.send(packet);
			socket.close();
		} catch (SocketException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}

  服務器接收端TCP須要經過ServerSocket與設備端口進行連接,接收Socket利用InputStream獲取數據;UDP依然利用DatagramSocket與端口連接,DatagramPacket獲取數據。server

   服務器端 - TCP對象

ServerSocket serverSocket=new ServerSocket(12345);
System.out.println("Create Serversocket");
////設置超時(未使用)
//serverSocket.setSoTimeout(5000);
//2>接受Socket
Socket socket=serverSocket.accept();
System.out.println("accept");
//3>獲取Socket的InoutStream
InputStream input=socket.getInputStream();
byte[] buffer=new byte[1024*4];
//4>讀取數據
input.read(buffer);
System.out.print(new String(buffer).trim());
//5>關閉Socket
socket.close();
serverSocket.close();
serverSocket=null;

   服務器端-UDPip

//1>構建DatagramSocket連接端口
DatagramSocket socket=new DatagramSocket(12345);
byte[] buffer=new byte[1024];
//2>構建DatagramPacket用於接收數據
DatagramPacket packet=new DatagramPacket(buffer, buffer.length);
//3>獲取數據
socket.receive(packet);
System.out.println("Receive");
//4>設置偏移量的方法,解決了傳輸數據中的亂碼問題
System.out.println(new String(packet.getData(),packet.getOffset(),packet.getLength()));
//5>必定要關閉,不然影響下次使用
socket.close();

常見問題:
路由

    1>ECONNREFUSED 問題 :這個問題困擾了我很久,其實處理起來比較容易,產生的緣由是端口被佔,或者ip錯誤,須要仔細檢查IP和端口號,端口號能夠設置大一些,1024一下的端口號容易被佔用。

    2>程序在socket建立或鏈接的時候程序崩潰 :我出現這種狀況大可能是服務器沒有開,而且使用的TCP協議,打開就行了

    3>服務器端接收不到數據 :我使用的是校園網和實驗室的無線網,只有兩種狀況能夠接受到數據,第一種,服務器和手機終端鏈接在同一個路由器上;第二種服務器鏈接在校園網上,手機鏈接沒有限制。緣由暫時還不太清除

相關文章
相關標籤/搜索