認識SOKET
Socket Library是BSD UNIX的一個API (Application Programming Interface),
Socket:兩個互相溝通的程序(process)之間的任一端點。
此兩個process可同屬一電腦系統之內,或分屬於兩個不同的電腦系統透過網路來溝通。
使用目的:網路應用程式設計者不需處理網路下層(傳輸層、網路層)的工作,而專注於其本身
(應用層)的程式設計。
JAVA 在使用SOCKT 時,有二種常用的方式
1.TCP: 它就像是雙掛號,對方沒有收到就會不斷嘗試再送給對方,
直到使用者中止或是俞時。
2.UDP : UDP則是類似一般的平信,通常都會送達,但還是會有不見的時候,但成本便宜,
無須等待對方回應即可繼續傳送。
(看過海角七號就知道)
Java TCP 的流程圖
伺服端ServerSocket 等待使用者的Socket來做連線,並取得輸出入通道。
MyServerSocket.java
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.InetAddress;
import java.net.ServerSocket;
import java.net.Socket;
public class MyServerSocket {
//宣告區
ServerSocket server;
ObjectInputStream in;
ObjectOutputStream out;
BufferedReader buffer;
Thread inputThread;
Thread recThread;
boolean isClose = false;
Socket client;
public MyServerSocket() {
try {
//ServerSocket Listen 在本機的5678 port
server = new ServerSocket(5678);
//輸出己啟動伺服器資訊
System.out.println("伺服器啟動於 : "
+ InetAddress.getLocalHost().getHostAddress() + ":"
+ server.getLocalPort());
//把連線過來的Client端交由另一個socket處理
client=server.accept();
//輸出訊息己有使用者連進來
System.out.println("Client is connected");
//將Server端的標準輸出入設為鍵盤
buffer=new BufferedReader(new InputStreamReader(System.in));
//取得與此使用者的輸出管道
out=new ObjectOutputStream(client.getOutputStream());
//取得與此使用者的輸入管道
in=new ObjectInputStream(client.getInputStream());
} catch (IOException e) {
e.printStackTrace();
}
//用一個執行序負毒處理接收到的訊息
recThread = new Thread(new Runnable() {
@Override
public void run() {
recMessage();
}
});
//啟動接收訊息執行序
recThread.start();
//使用一個執行序來處理Server端的鍵盤輸入
inputThread = new Thread(new Runnable() {
@Override
public void run() {
keyin();
}
});
//啟動server端輸入執行序
inputThread.start();
}
//Server端鍵盤處理函式
private void keyin() {
try {
String line;
while (!(line = buffer.readLine()).equals("-1")) {
System.out.println("傳送:" + line);
write(line);
Thread.sleep(100);
}
isClose = true;
close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
//接收訊息處理函式
private void recMessage() {
String recText = "";
while (!isClose) {
try {
recText = in.readUTF();
System.out.println("接收:" + recText);
Thread.sleep(100);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
輸出資料到client端函式
private void write(String text) {
try {
out.writeUTF(text);
out.flush();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
private void close() {
try {
recThread.interrupt();
inputThread.interrupt();
out.flush();
out.close();
in.close();
client.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
//主程式
public static void main(String arg[])
{
new MyServerSocket();
}
}
MySocket.java
import java.io.IOException;
import java.net.Socket;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.UnknownHostException;
public class MySocket {
Socket client;
ObjectInputStream in;
ObjectOutputStream out;
BufferedReader buffer;
Thread inputThread;
Thread recThread;
boolean isClose = false;
public MySocket() {
String ServerIP = "127.0.0.1";
try {
client = new Socket(ServerIP, 5678);
in = new ObjectInputStream(client.getInputStream());
out = new ObjectOutputStream(client.getOutputStream());
buffer = new BufferedReader(new InputStreamReader(System.in));
} catch (IOException e) {
e.printStackTrace();
}
recThread = new Thread(new Runnable() {
@Override
public void run() {
recMessage();
}
});
recThread.start();
inputThread = new Thread(new Runnable() {
@Override
public void run() {
keyin();
}
});
inputThread.start();
}
private void keyin() {
try {
String line;
while (!(line = buffer.readLine()).equals("-1")) {
System.out.println("傳送:" + line);
write(line);
Thread.sleep(100);
}
isClose = true;
close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
private void recMessage() {
String recText = "";
while (!isClose) {
try {
recText = in.readUTF();
System.out.println("接收:" + recText);
Thread.sleep(100);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
private void write(String text) {
try {
out.writeUTF(text);
out.flush();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
private void close() {
try {
recThread.interrupt();
inputThread.interrupt();
out.flush();
out.close();
in.close();
client.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public static void main(String args[]) {
new MySocket();
}
}
Java UDP 流程圖
直接傳送過去,並沒有任何的驗證機制。
UDPServer.java
import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.net.SocketException;
import java.net.UnknownHostException;
public class UDPServer {
boolean isClose = false;
byte[] Bytebuffer = new byte[65507];
DatagramPacket dp = new DatagramPacket(Bytebuffer, Bytebuffer.length);
DatagramSocket ds;
Thread recThread;
public UDPServer() {
try {
ds = new DatagramSocket(5678);
System.out.println("伺服器啟動於 : "
+ InetAddress.getLocalHost().getHostAddress() + ":"
+ ds.getLocalPort());
recThread = new Thread(new Runnable() {
@Override
public void run() {
recMessage();
}
});
recThread.start();
} catch (SocketException e) {
e.printStackTrace();
} catch (UnknownHostException e) {
e.printStackTrace();
}
}
private void recMessage() {
try {
String msg = "";
while (!isClose) {
ds.receive(dp);
msg = new String(dp.getData(), 0, dp.getLength());
System.out.println("傳來的訊息 : " + msg);
Thread.sleep(100);
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public static void main(String args[]) {
new UDPServer();
}
}
UDPClient.java
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.net.SocketException;
import java.net.UnknownHostException;
public class UDPClient {
DatagramPacket dp;
DatagramSocket ds;
Thread inputThread;
BufferedReader buffer;
public UDPClient() {
System.out.println("請輸入要傳送的訊息 : ");
String msg = "Key in";
buffer = new BufferedReader(new InputStreamReader(System.in));
try {
ds=new DatagramSocket();
} catch (SocketException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
inputThread = new Thread(new Runnable() {
@Override
public void run() {
keyin();
}
});
inputThread.start();
}
private void keyin() {
try {
String line;
while (!(line = buffer.readLine()).equals("-1")) {
System.out.println("傳送:" + line);
write(line);
Thread.sleep(100);
}
} catch (IOException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
private void write(String text) {
try {
dp = new DatagramPacket(text.getBytes(), text.getBytes().length,
InetAddress.getByName("127.0.0.1"), 5678);
ds.send(dp);
} catch (UnknownHostException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public static void main(String args[])
{
new UDPClient();
}
}
參考資料:
https://sites.google.com/a/mis.nsysu.edu.tw/cheng-shi-zi-xun-wang/java-jin-jie-pian/wang-lu-pian/1-shen-me-shisocket
部份圖片來自網路,若有侵權請來信告知。