2014-10-19 4 views
0

Я хочу определить порт открытым.Почему selector.select() всегда возвращается 0

InetSocketAddress address = new InetSocketAddress("www.google.com", 80); 
Selector selector = Selector.open(); 
SocketChannel socketChannel = SocketChannel.open(); 
socketChannel.configureBlocking(false); 
socketChannel.connect(address); 
socketChannel.register(selector, SelectionKey.OP_WRITE); 
int result = selector.select(); 
System.out.println(result); 

Если порт не открыт, думаю, я смотрю таки вернуть 0, но когда порт открыт, он также вернет 0, я ожидаю, что это может вернуть 1.

+0

Не знаю ничего об этом, но может быть, потому что вы указали configureBlocking (false) - означает ли это, что операция асинхронна и вы не знаете, когда она закончится? – RenniePet

+0

Я думаю, что это будет возврат 1 при выполнении этого кода, потому что канал записи готов. Но он возвращает 0, поэтому я настолько смущен. @ RenniePet – firebroo

+0

почему другой ответ был удален? – firebroo

ответ

1

Это потому, что вы «выбор неправильного события. Вы должны были зарегистрировать канал для OP_CONNECT.. Затем, когда вы его получите, позвоните по телефону finishConnect(), и если он вернет истинный регистратор OP_CONNECT и зарегистрирует любое интересующее вас событие, то есть OP_READ или OP_WRITE.

Обратите внимание, что если finishConnect() возвращает false, вы должны просто продолжать выбирать, и если это вызывает исключение, соединение потерпело неудачу, и вы должны закрыть канал.

Если вы хотите избежать всех этих осложнений, обычно проще выполнить соединение, находясь в режиме блокировки, а затем перевести канал в неблокирующий режим и выбрать.

Несмотря на то, что в использовании NIO действительно совсем мало смысла в использовании клиента.

См. here для получения более полной версии этого ответа.

+0

когда я использую socketChannel.register (селектор, SelectionKey.OP_CONNECT); int result = selector.select(); System.out.println (результат); Он всегда возвращает 1, открыт ли порт, поэтому, когда порт закрыт, какое событие будет готово, почему оно также возвращает 1. @ EJP – firebroo

+0

Потому что он хочет, чтобы вы назовем 'finishConnect(), как описано выше. Так и сделайте это. Тогда вы либо получите правду, либо ложь, либо исключение. – EJP