UDP多播压力测试,发现并不节省网络流量与广播同样???已分享代码,求解决

用java做了个UDP多播压力测试

发现即使其他主机没有加入多播IP组也会受到阻塞网络,无法与其他主机网络通讯。

在这里插入图片描述

另外一个测试,用UDP点对点(单播)压力测试,其他主机是不受影响的

从这测试结果来看,UDP多播可能IP底层多播与广播没有区别同样会占用局域网内的所有主机的带宽。

希望大神能给个解释,是测试有问题还是多播IP底层确实与广播一样?

代码:

Main.java

package com.main;

import com.network.udp.MulticastServer;
import com.network.udp.UdpCallback;
import com.network.udp.UdpServer;

public class Main {

	static UdpServer udp;
	static MulticastServer multi1;

	public static void main(String[] args) {
		udp = new UdpServer(udpcall);
		udp.start(8000);
		
		multi1 = new MulticastServer(multicall1);
		multi1.start("224.100.100.1", 9000); //UDP多播地址与端口

		byte[] data = new byte[(20 * 1024)];
		while(true){
			//udp.send("192.168.88.227", 1001, data, data.length); //UDP点对点压力测试
			multi1.send(9001, data, data.length); //UDP多播压力测试,发送数据
		}
	}
	
	public static UdpCallback udpcall = new UdpCallback() {
		public void onReceive(int port, byte[] data, int length) {
			System.out.print("1onReceive port : " + port + ", length : " + length );
			System.out.print("\r");
		}
	};
	
	public static UdpCallback multicall1 = new UdpCallback() {
		public void onReceive(int port, byte[] data, int length) {
			System.out.print("2onReceive port : " + port + ", length : " + length );
			System.out.print("\r");
		}
	};
	
	public static UdpCallback multicall2 = new UdpCallback() {
		public void onReceive(int port, byte[] data, int length) {
			System.out.print("3onReceive port : " + port + ", length : " + length );
			System.out.print("\r");
		}
	};
	
}

UdpCallback.java

package com.network.udp;

public interface UdpCallback {
	public void onReceive(int port, byte[] data, int length);
}

MulticastServer.java

package com.network.udp;

import java.io.IOException;
import java.net.DatagramPacket;
import java.net.InetAddress;
import java.net.MulticastSocket;
import java.net.UnknownHostException;

public class MulticastServer {
	private final int MAX_SIZE = (1000 * 1024);// 1000Kb限制
	private int port = 8888;
	private String address = "224.0.0.1";
	private MulticastSocket multicastSocket = null;
	private UdpCallback call;
	

	public MulticastServer(UdpCallback call) {
		// TODO 自动生成的构造函数存根
		this.call = call;
	}

	public void start(String address, int port) {
		this.address = address;
		this.port = port;
		receiveMessage();
	}

	public void stop() {
		if (multicastSocket != null) {
			multicastSocket.close();
		}
	}

	public void send(int port, byte[] data, int length) {
		if (multicastSocket != null) {
			try {
				InetAddress group = InetAddress.getByName(address);
				DatagramPacket datagramPacket = new DatagramPacket(data, length, group, port);
				multicastSocket.send(datagramPacket);
			} catch (UnknownHostException e) {
				// TODO 自动生成的 catch 块
				e.printStackTrace();
			} catch (IOException e) {
				// TODO 自动生成的 catch 块
				e.printStackTrace();
			}
		}
	}

	private void receiveMessage() {
		if (multicastSocket != null) {
			stop();
		}
		new Thread() {
			public void run() {
				byte[] buffer;
				DatagramPacket datagramPacket = null;
				try {
					InetAddress group = InetAddress.getByName(address);
					multicastSocket = new MulticastSocket(port);
					multicastSocket.joinGroup(group);
					buffer = new byte[MAX_SIZE];
					datagramPacket = new DatagramPacket(buffer, buffer.length);
				} catch (UnknownHostException e) {
					// TODO 自动生成的 catch 块
					e.printStackTrace();
					return;
				} catch (IOException e) {
					// TODO 自动生成的 catch 块
					e.printStackTrace();
					return;
				}
				while (true) {
					try {
						multicastSocket.receive(datagramPacket);
					} catch (IOException e) {
						// TODO 自动生成的 catch 块
						e.printStackTrace();
						break;
					}
					
					if (datagramPacket.getLength() != 0) {
						call.onReceive(datagramPacket.getPort(), datagramPacket.getData(), datagramPacket.getLength());
					}
				}
				multicastSocket.close();
				multicastSocket = null;
			}
		}.start();
	}

}

UdpServer.java

package com.network.udp;

import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.net.SocketException;

public class UdpServer {
	private final int MAX_SIZE = (1000 * 1024);// 1000Kb限制
	private UdpCallback call = null;
	private boolean rxThread = false;
	private DatagramSocket socket = null;
	public int port = 8080;
	public String group = null;

	public UdpServer(UdpCallback call) {
		// TODO 自动生成的构造函数存根
		this.call = call;
	}

	public void start(int port) {
		this.port = port;
		receiveMessage();
	}

	public void start(String group, int port) {
		this.group = group;
		this.port = port;
		receiveMessage();
	}

	public void stop() {
		if (socket != null) {
			rxThread = false;
			socket.close();
			socket = null;
		}
	}

	private void receiveMessage() {
		if (socket != null) {
			stop();
		}
		new Thread() {
			public void run() {
				byte[] receBuf;
				DatagramPacket packet;
				try {
					socket = new DatagramSocket(port);
					socket.setSendBufferSize(MAX_SIZE);
					socket.setReceiveBufferSize(MAX_SIZE);
					receBuf = new byte[MAX_SIZE];
					packet = new DatagramPacket(receBuf, receBuf.length);
					rxThread = true;
				} catch (SocketException e) {
					// TODO 自动生成的 catch 块
					e.printStackTrace();
					return;
				}

				while (rxThread) {
					try {
						socket.receive(packet);
						
					} catch (IOException e) {
						e.printStackTrace();
						break;
					}
					if (packet.getLength() != 0) {
						call.onReceive(packet.getPort(), packet.getData(), packet.getLength());
					}
				}
				socket.close();
				socket = null;
			}
		}.start();
	}

	public void send(String ip, int port, byte[] data, int length) {
		if (socket != null) {
			try {
				InetAddress serverAddress = InetAddress.getByName(ip);
				DatagramPacket pack = new DatagramPacket(data, length, serverAddress, port);
				socket.send(pack);
			} catch (IOException e) {
				// TODO 自动生成的 catch 块
				e.printStackTrace();
			}
		}
	}

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值