0

我正在为android编写一个java套接字程序:

DeviceManagerWindow.java

public class DeviceManagerWindow extends Activity
{
    Thread sendMulticast;
    ...
    ...
    WifiManager wifi = (WifiManager)getSystemService( Context.WIFI_SERVICE );
    if(wifi != null)
    {
        WifiManager.MulticastLock lock = wifi.createMulticastLock("WifiDevices");
        lock.acquire();
    }
    public void searchDevice(View view)
    {
        sendMulticast = new Thread(new MultiCastThread());
        sendMulticast.start();
        ExecutorService executorService = Executors.newFixedThreadPool(1);
        List<Future<DeviceDetails>> deviceList = new ArrayList<Future<DeviceDetails>>();

            Callable<DeviceDetails> device = new MulticastReceiver();
            Future<DeviceDetails> submit = executorService.submit(device);
            deviceList.add(submit);

        DeviceDetails[] devices = new DeviceDetails[deviceList.size()];
        int i=0;
        for(Future<DeviceDetails> future :deviceList)
        {
            try
            {
                devices[i] = future.get();
            }
            catch(Exception e)
            {
                Log.v("future Exception: ",e.toString());
            }
        }
        listAllDevices(devices);
    }
}

在接收器类中,我有以下代码:

MultivastReceiver.java

public class MulticastReceiver implements Callable<DeviceDetails>
{
    DatagramSocket socket = null;
    DatagramPacket inPacket = null;
    public MulticastReceiver()
    {
        try
        {
            socket = new DatagramSocket(5500);
        }
        catch(Exception ioe)
        {
            System.out.println(ioe);
        }
    }
    @Override
    public DeviceDetails call() throws Exception
    {
        // TODO Auto-generated method stub
        try
        {
                byte[] inBuf = new byte[WifiConstants.DGRAM_LEN];
                //System.out.println("Listening");
                inPacket = new DatagramPacket(inBuf, inBuf.length);
                socket.receive(inPacket);

                String msg = new String(inBuf, 0, inPacket.getLength());

                Log.v("Received: ","From :" + inPacket.getAddress() + " Msg : " + msg);
                DeviceDetails device = getDeviceFromString(msg);
                return device;
        }
        catch(Exception e)
        {
            Log.v("Receiving Error: ",e.toString());
            return null;
        }
    }
    public DeviceDetails getDeviceFromString(String str)
    {
        String type;
        String IP;
            type=str.substring(0,str.indexOf('`'));
            str = str.substring(str.indexOf('`')+1);
            IP=str;
        DeviceDetails device = new DeviceDetails(type,IP);
        return device;
    }
}

现在,上面的代码仅在收到第一个数据包时才搜索第一个数据包,它停止搜索下一个数据包。我希望它监听传入的数据包 30 秒,然后退出,它收到的所有数据。怎么做。

如果我使用无限循环,那么它将永远不会返回值,因为 return 语句将放在循环之外,如果我将 return 语句放在循环内,它将返回值并且永远不会等待下一个数据包的到来。

4

3 回答 3

1

有2种可能性。

您可以将套接字设置为 30 秒后超时。不幸的是,每次您收到新消息时都会重置。所以如果你知道所有的消息都会在 30 秒内到达,只需设置超时,套接字最终会在收到最后一个数据包后超时。

链接到套接字超时

第二种选择是使用单独的 TimerTask 来唤醒您的客户端,这样它就不会在接收中无限期地被阻塞。您将需要从应该完成这项工作的计时器任务中中断客户端线程。

链接到定时器任务

在这两种情况下,您都需要处理适当的异常来处理超时。

于 2013-04-09T13:42:34.253 回答
0

创建一个默认为 false 的“取消”布尔属性,并让您的 while 循环运行,直到该属性设置为 true。然后我们一个计时器在三十秒后将“取消”设置为真。

于 2013-04-09T13:37:19.190 回答
0

我在这里给了你代码......

我猜这是同样的问题。不记号啊!!看看你是否认为这很好。

于 2013-04-10T22:16:23.287 回答