Socket编程总结(1)
程序员文章站
2022-07-15 18:44:21
...
基本套接字
套接字主要是用于处理端到端数据传输,即应用程序用它来发送和接收数据。使用Socket可以将应用程序添加到网络,并与处于同一网络的其他应用程序进行通信。一台计算机上应用程序向Socket写入的信息可以被另外一台计算机的另一个应用读取。
套接字地址,包括了目的IP地址和端口号。
一、TCP套接字
Java为TCP协议提供了两个类,Socket和ServerSocket类,后者主要用于服务端,监听TCP连接请求。客户端只需要使用Socket实例进行通信,而服务端需要使用两个类的实例。典型的TCP客户端要经过以下三步:
1、创建一个Socket实例:指定IP地址和目的端口,建立一个TCP连接;
2、通过套接字(Socket实例)的输入输出流(OutputStream和InputStream)进行通信;
3、使用Socket类的close()方法关闭连接。
下面是TCP客户端的代码:
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.Socket;
import java.net.SocketException;
public class TCPEchoClient {
public static void main(String[] args) throws IOException {
Socket socket = new Socket("10.112.154.154",9000);
System.out.println("正在连接服务器...");
InputStream in = socket.getInputStream();
OutputStream out = socket.getOutputStream();
byte[] data = "send message".getBytes();
out.write(data);
int total = 0;
int bytes;
while(total<data.length){
if((bytes = in.read(data,total,data.length-total))==-1)
throw new SocketException("关闭连接");
total += bytes;
}
System.out.println("received:" + new String(data));
socket.close();
}
}
TCP服务端则需要考虑以下几步:1、创建一个ServerSocket并指定本地端口,该套接字功能是侦听该指定端口收到的连接;
2、重复执行:
a、调用ServerSocket的accept()方法获取下一个客户端连接,并创建Socket实例,由accept()方法返回;
b、使用返回的Socket实例的输入输出流与客户端通信;
c、通信完成后,使用Socket类的close()方法关闭该客户端套接字连接。
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.net.SocketAddress;
public class TCPEchoServer {
private static final int BUFSIZE = 32;
public static void main(String[] args) throws IOException {
ServerSocket serverSocket = new ServerSocket(9000);
int recvMsgSize;
byte[] receiveBuf = new byte[BUFSIZE];
while(true){
Socket clntSocket = serverSocket.accept();
SocketAddress clientAddress = clntSocket.getRemoteSocketAddress();
System.out.println("在该地址处理用户请求:"+clientAddress);
InputStream in = clntSocket.getInputStream();
OutputStream out = clntSocket.getOutputStream();
while ((recvMsgSize = in.read(receiveBuf)) !=-1) {
out.write(receiveBuf,0,recvMsgSize);
}
clntSocket.close();
}
}
}
二、UDP套接字
1、UDP客户端。典型的UDP客户端主要执行以下三步:
a、创建一个DatagramSocket实例;
b、使用DatagramSocket的send()和receive()方法发送和接收DatagramSocket实例进行通信;
c、通信完成后,使用DatagramSocket类的close()方法来销毁套接字。
客户端代码如下:
import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.net.SocketException;
public class UDPEchoClientTimeout {
private static final int TIMEOUT = 3000;
private static final int MAX = 5;
public static void main(String[] args) throws IOException {
byte[] bytesToSend = "sendsmessage".getBytes();
DatagramSocket socket = new DatagramSocket();
socket.setSoTimeout(TIMEOUT);
InetAddress address = InetAddress.getByName("10.112.154.154");
DatagramPacket sendPacket = new DatagramPacket(bytesToSend, bytesToSend.length,address, 9002);
DatagramPacket receivePacket = new DatagramPacket(new byte[bytesToSend.length], bytesToSend.length);
int tries = 0;
boolean receivedResponse = false;
do{
socket.send(sendPacket);
try {
socket.receive(receivePacket);
if(!receivePacket.getAddress().equals(address)){
throw new IOException("接收到未知来源的消息");
}
receivedResponse = true;
} catch (Exception e) {
System.out.println(e.getMessage());
tries += 1;
System.out.println("超时,还有" + (MAX-tries) + "次机会");
}
}while((!receivedResponse) && (tries<MAX));
if(receivedResponse){
System.out.println("Received:" + new String(receivePacket.getData()));
}else{
System.out.println("没有接收到数据");
}
socket.close();
}
}
UDP服务器端代码如下:
import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.SocketException;
public class UDPEchoServer {
private static final int ECHOMAX = 255;
public static void main(String[] args) throws IOException {
DatagramSocket socket = new DatagramSocket(9002);
DatagramPacket packet = new DatagramPacket(new byte[ECHOMAX], ECHOMAX);
while(true){
socket.receive(packet);
System.out.println("在该地址处理用户请求:" + packet.getAddress().getHostAddress() + "端口号:" + packet.getPort());
System.out.println("接收到的数据是:"+new String(packet.getData()));
socket.send(packet);
packet.setLength(ECHOMAX);
}
}
}
上一篇: 类和对象 关于继承 关于接口
下一篇: PY__11 类和对象 继承