java udp 工具类_Java 使用UDP、TCP进行网络通信

UDP

工具类

public classUDP {private static final int port = 9000; //要使用的端口号

/*** 发送消息

* @Param ip 对方的ip,String

* @Param msg 要发送的消息,String类型*/

public static void send(String ip,String msg) throwsIOException {//对方的ip,不能直接用String,需要转换一下

InetAddress ipAddr =InetAddress.getByName(ip);//socket,相当于码头

DatagramSocket socket = newDatagramSocket();//packet,数据包,相当于集装箱//参数:byte[]、数据长度、对方ip(不能直接写String)、要使用的端口号//什么类型都可以传输,比如传文件,不局限于String,因为都要转换为字节数组

DatagramPacket packet = newDatagramPacket(msg.getBytes(), msg.length(),ipAddr,port);//通过socket发送packet

socket.send(packet);

System.out.println("send:"+msg);//关闭socket

socket.close();

}/***监听端口,接收消息*/

public static void receive() throwsIOException {//socket,指定要监听的端口。发送、接收使用的端口要相同

DatagramSocket socket = newDatagramSocket(port);//packet,用一个byte[]来存储数据//第一个数值是字节数组的长度,第二个数值是要读取的字节数,把读取到的数据放到byte[]中//读取的字节数要小于等于byte[]的长度,不然放不下

DatagramPacket packet = new DatagramPacket(new byte[1024], 1024);//一直监听

while (true){

socket.receive(packet);//通过socket接收packet,用packet来封装接收到的数据,没接收到数据时会一直阻塞

byte[] data = packet.getData(); //获取packet中的数据(整个byte[])

int length = packet.getLength(); //获取数据的实际长度。packet中的byte[]不一定是装满的,需要获取实际的字节数

String msg= new String(data, 0, length); //byte[]、offset、length//msg = new String(data);//其实不获取实际长度也行

System.out.println("received:"+msg);//获取本机ip、发送方ip//InetAddress localAddress = socket.getLocalAddress();//本机//InetAddress address = packet.getAddress();//发送方//String ip = address.getHostAddress();//String类型的ip//socket.close();//关闭socket//一直监听,不关闭socket//退出聊天时,比如退出桌面程序或web项目点击“结束聊天”、超过2分钟未互动,需要关闭socket

}

}

}

UDP不区分客户端、服务端,2边使用的socket都是DatagramSocket,使用的packet都是DatagramPacket。发送、接收可以使用同一个socket。

发送消息

public classSend {public static void main(String[] args) throwsIOException {

UDP.send("127.0.0.1", "hello");}

}

接收消息

public classReceive {public static void main(String[] args) throwsIOException {

UDP.receive();

}

}

先启动接收方,再启动发送方。

有一个问题:写了2个主类,分别启动,一般不这么干,使用多线程代替。

测试类

public classTest {public static void main(String[] args) throwsIOException, InterruptedException {//开启一条线程,监听端口、接收消息

Thread receiveThread = new Thread(newRunnable() {

@Overridepublic voidrun() {try{

UDP.receive();

}catch(IOException e) {

e.printStackTrace();

}

}

});

receiveThread.start();//怕接收线程暂时没分配到时间片,在发送消息之后才执行,没能接收到掐前面的消息,可以让发送消息的线程沉睡会儿

Thread.sleep(100);//也可以单独开启一条线程来发送消息

UDP.send("127.0.0.1","hello");}

}

UDP是不可靠的,不管对方ip存不存在、对方有没有启动监听,直接发出去,不管对方能不能接收到。

TCP

工具类

public classTCP {private static final int port = 9000; //要使用的端口号

/*** 发送消息

* @Param ip 对方的ip,String

* @Param msg 要发送的消息,String类型*/

public static void send(String ip,String msg) throwsIOException {//客户端的socket。直接使用String类型的对方的ip

Socket socket = newSocket(ip, port);//向服务端发送数据

OutputStream os = socket.getOutputStream(); //输出流

os.write(msg.getBytes()); //byte[]

System.out.println("send:"+msg);

}/***监听端口,接收消息*/

public static void receive() throwsIOException {//服务端的socket,指定要监听的端口

ServerSocket serverSocket = newServerSocket(port);//一直监听

while (true) {//接收客户端的请求,并创建一个与之对应的Socket来与该客户端通信

Socket socket =serverSocket.accept();//接收客户端发送的数据

InputStream is =socket.getInputStream();byte[] buff = new byte[1024];int length = is.read(buff); //将数据读取到byte[]中,返回读取到的字节数

java.lang.String msg = new java.lang.String(buff, 0, length); //有很多个String类,不要导错了

System.out.println("received:" +msg);//获取本机ip、发送方ip//InetAddress localAddress = socket.getLocalAddress();//本机//InetAddress inetAddress = socket.getInetAddress();//发送方//String ipAddress = localAddress.getHostAddress();//获取String类型的IP//socket.close();

}

}

}

TCP要区分客户端、服务端,客户端用Socket,服务端用ServerSocket,通过ServerSocket获取与客户端对应的socket,来与客户端通信。

客户端、服务端是相对的,发送数据的一方叫做客户端,接收消息的一方叫做服务端,一般都要客户端、服务端。

接收到对方消息后,可以调用send()传入对方ip与之通信,也可以写个重载的send(),传入与客户端对应的socket。

测试类

public classTest {public static void main(String[] args) throwsIOException, InterruptedException {//开启一条线程,监听端口、接收消息

Thread receiveThread = new Thread(newRunnable() {

@Overridepublic voidrun() {try{

TCP.receive();

}catch(IOException e) {

e.printStackTrace();

}

}

});

receiveThread.start();//怕接收线程暂时没分配到时间片,在发送消息之后才执行,没能接收到掐前面的消息,可以让发送消息的线程沉睡会儿

Thread.sleep(100);//也可以单独开启一条线程来发送消息

TCP.send("127.0.0.1","hello");

}

}

TCP是可靠的,三次握手确定双方可以正常通信。

你可能感兴趣的:(java,udp,工具类)