使用Selector java无法从两个套接字读取

时间:2013-10-28 05:51:46

标签: java nio serversocket

我有一个像bellow一样的代码:

Bytebuffer buffer1 = ByteBuffer.allocate(1024);   Bytebuffer buffer2 = ByteBuffer.allocate(1024);

而(真)   {

selector.select();
System.out.println("Ready Selector: "+num);
Set<SelectionKey> selectedKeys = selector.selectedKeys();
Iterator it = selectedKeys.iterator();


while(it.hasNext())
   {

   SelectionKey key= (SelectionKey) it.next();

   if(key.isReadable())
    {

      if(key.attachment.toString("Socket1")
         {
            //read data and store in buffer 1
            SocketChannel channel1= (SocketChannel) key.channel();
             while (true) {

             int number_of_bytes=channel1.read(buffer1);                             
                          if (number_of_bytes <= 0) {
                              System.out.println("Number of bytes: "+number_of_bytes);
                              if(number_of_bytes==-1)
                              {
                                  key.cancel();
                                  channel1.close();
                              }
                            break;
                          } 

         }
     else if(key.attachment.toString("Socket2")
         {
            //read data and store in buffer 2

SocketChannel channel2 =(SocketChannel)key.channel();

             while (true) {

             int number_of_bytes=channel1.read(buffer2);                             
                          if (number_of_bytes <= 0) {
                              System.out.println("Number of bytes: "+number_of_bytes);
                              if(number_of_bytes==-1)
                              {
                                  key.cancel();
                                  channel2.close();
                              }
                            break;
                          } 

         }
       }
} 

现在我面临的问题是,我只从一个套接字获取数据。就像我先打开socket1并输入一些数据一样。我可以在上面的代码中读取该数据,但不读取socket2数据。再次,如果我首先运行socket2然后再运行socket1,我可以读取socket2数据,但无法读取socke1数据。请帮我找出代码中的错误..

1 个答案:

答案 0 :(得分:0)

如果没有看到更多代码,就无法说出你的问题,但你的选择循环应该是这样的:

while(it.hasNext())
{
    SelectionKey key= (SelectionKey) it.next();
    it.remove();
    if (!key.isValid())
        continue;
    if(key.isReadable())
    {
        SocketChannel sc = (SocketChannel)key.channel();
        // read the channel
    }
}

您根本不需要String附件;你需要检查每个密钥的有效性;并且您需要在处理时从所选键集中删除每个键。

如果您的代码仍然不能正常工作,则其他地方也有问题,或者没有人发送到第二个连接。

编辑:重新编辑,如果读取零字节,则必须退出读取循环;否则你只是在没有任何事可做的情况下盲目地旋转,并使其他渠道挨饿。您无需取消密钥:关闭频道即可