组播
将同一网络段的设备进行逻辑上的分组。如设定一个组播地址,所有进入该地址的设备是同一个组。任意一个设备向该组发送消息即为组播。
广播
将消息发送给局域网中的每一个设备即为广播。
组播与广播最大的不同在于发送消息的地址不同。
代码示例:
发送端
fun sendMultiBroadcast() {
if (multicastLock?.isHeld!!) {
var multicastSocket = MulticastSocket(8600)
var address = InetAddress.getByName(IP_ADDRESS)
if (!address.isMulticastAddress) {
Log.d(TAG, "该地址不是组播地址")
}
multicastSocket.joinGroup(address)
var datagramPacket: DatagramPacket?
val buf = "hah i changed already".toByteArray()
datagramPacket = DatagramPacket(buf, buf.size, address, 8600) // 本地的socket端口为8600,所以该socket也可以接收来自自已的消息
while (true) {
multicastSocket.send(datagramPacket) // 在发送时候如果切换网络,则报java.io.IOException: Network is unreachable错误,注意
Thread.sleep(2000)
Log.i(TAG, "发送消息到8600端口")
}
multicastSocket.leaveGroup(address)
multicastSocket.close()
}
}
有的网络资料显示,android默认不接收组播消息,需要手动打开。如下代码所示:
var wifiManager: WifiManager? = null
var multicastLock: WifiManager.MulticastLock? = null
/**
* 获取multicast锁,网络资料表明android为了节约电量,默认不接收组播消息。
*
* 但经过实际demo运行显示,屏蔽该代码,一台三星和一台华为平板之间也是可以正常通信的。
*/
private fun openMulticastLock() {
wifiManager = applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager
multicastLock = wifiManager?.createMulticastLock("multicast.test")
multicastLock?.acquire()
}
接收端代码如下:
fun sendMultiBroadcast() {
if (multicastLock?.isHeld!!) {
var multicastSocket = MulticastSocket(8600)
multicastSocket.timeToLive = 254
var address = InetAddress.getByName(IP_ADDRESS)
if (!address.isMulticastAddress) {
Log.d(TAG, "该地址不是组播地址")
}
multicastSocket.joinGroup(address)
Log.i(TAG, "加入组播")
val rev = ByteArray(512)
var revPacket = DatagramPacket(rev, rev.size)
try {
multicastSocket.receive(revPacket)
} catch (e: Exception) {
Log.e(TAG, "接收错误", e)
}
Log.i(TAG, "data is " + String(revPacket.data))
mMainHandler.post {
tv_msg.text = String(revPacket.data) + revPacket.address.hostAddress
}
multicastSocket.leaveGroup(address)
multicastSocket.close()
}
}
companion object {
const val TAG = "sx"
const val IP_ADDRESS = "239.0.0.1"
const val SEND_ID = 0x0001
}
其中,发送端和接收端的ip地址和端口要一致。
两台设备如果同在一个局域网内可以通过此种方法通信。