TCP實現訊息傳遞
阿新 • • 發佈:2020-12-18
技術標籤:java全棧記錄
分別實現client和server, 完成訊息傳遞功能
(簡易版本, 作為學習記錄
client端
import java.io.IOException;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;
import java.nio.charset.StandardCharsets;
public class TCPclient {
public static void main(String[] args) {
int port = 9999;
Socket socket = null;
OutputStream outputStream = null;
try {
InetAddress inetAddress = InetAddress.getByName("127.0.0.1");
socket = new Socket(inetAddress, port);
outputStream = socket.getOutputStream();
outputStream.write("oula".getBytes());
} catch (UnknownHostException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (socket != null){
try {
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if(outputStream != null){
try {
outputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
解釋:
- socket作為連結通道開啟指定IP和埠, 需要與伺服器端一致
- 作為socket類包含輸出流方法, 用outputstream承接輸出流,
- OutputStream輸出字串的字元流形式到服務端
server端
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.ServerSocket;
import java.net.Socket;
public class TCPServer {
public static void main(String[] args) {
int port = 9999;
ServerSocket serverSocket = null;
Socket socket = null;
InputStream inputStream = null;
ByteArrayOutputStream baos = null;
try {
serverSocket = new ServerSocket(port);
socket = serverSocket.accept();
inputStream = socket.getInputStream();
baos = new ByteArrayOutputStream();
byte[] buffer = new byte[1024];
int len;
while((len = inputStream.read(buffer)) != -1){
baos.write(buffer, 0, len);
}
System.out.println(baos.toString());
} catch (IOException e) {
e.printStackTrace();
} finally {
if (serverSocket != null){
try {
serverSocket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (socket != null){
try {
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (inputStream != null){
try {
inputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (baos != null){
try {
baos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
解釋
- 設定serversocket, 指定開啟port埠
- 用accept方法阻塞接收客戶端埠的連線請求
- inputstream承接socket的輸入流
- 因為接收的是位元組流, 用ByteArrayOutputStream接收輸入進來的位元組流(相當於存放輸入進來的資料的一個變數)
- 列印的時候轉toString
效果
服務端接收到並列印了"尤拉"
如果想要按輸入的字串作為傳遞訊息, 該如何實現?
做一些修改即可
client端
import java.io.IOException;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;
import java.nio.charset.StandardCharsets;
import java.util.Scanner;
public class TCPclient {
public static void main(String[] args) {
int port = 9999;
Socket socket = null;
OutputStream outputStream = null;
try {
InetAddress inetAddress = InetAddress.getByName("127.0.0.1");
Scanner scanner = new Scanner(System.in);
System.out.println("input quit to exit");
while(true){
socket = new Socket(inetAddress, port);
outputStream = socket.getOutputStream();
String message = scanner.next();
if(message.equals("quit")) break;
else{
outputStream.write(message.getBytes());
socket.close();
outputStream.close();
}
}
} catch (UnknownHostException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (socket != null){
try {
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if(outputStream != null){
try {
outputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
server端
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.ServerSocket;
import java.net.Socket;
public class TCPServer {
public static void main(String[] args) {
int port = 9999;
ServerSocket serverSocket = null;
Socket socket = null;
InputStream inputStream = null;
ByteArrayOutputStream baos = null;
try {
byte[] buffer = new byte[1024];
int len;
while(true){
serverSocket = new ServerSocket(port);
socket = serverSocket.accept();
inputStream = socket.getInputStream();
baos = new ByteArrayOutputStream();
while((len = inputStream.read(buffer)) != -1){
baos.write(buffer, 0, len);
}
System.out.println(baos.toString());
serverSocket.close();
socket.close();
inputStream.close();
baos.close();
}
} catch (IOException e) {
e.printStackTrace();
} finally {
if (serverSocket != null){
try {
serverSocket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (socket != null){
try {
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (inputStream != null){
try {
inputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (baos != null){
try {
baos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
採用的是迴圈建立連線, 每次發一條訊息的方式實現, 但是如何在單次連線時傳送多條訊息還不懂, 思路是服務端需要監聽輸入流, 有輸入時觸發一次列印, 但是如何監聽輸入流, 尚待解決
效果