我使用SocketChannel
從客戶端的服務器接收TCP流。例如:如何切換socketchannel的阻塞模式?
Selector selector=Selector.open();
SocketChannel mychannel=SocketChannel.open(new InetSocketAddress(ip,port));
channel.configureBlocking(false);
SelectionKey channelkey=channel.register(selector,SelectionKey.OP_READ);
然後,我可以使用selector.select()
方法來處理讀取問題。
while(true){
if(selector.select()!=0){
Iterator<SelectionKey> it=selector.selectedKeys().iterator();
while(it.hasNext()){
SelectionKey key=it.next();
it.remove();
if(key.isReadable()){
if(key.equals(channelkey)){
//concrete handle
...
}
}
}
}
}
混凝土手柄,考慮到我想使用的InputStream(我想讀的流線)從服務器端接收TCP流,有兩個methods.One使用channel.socket()
,另一種是使用渠道。這裏我用channel.socket()
,例如:
SocketChannel channel = (SocketChannel) key.channel();
key.cancel();
channel.configureBlocking(true);
InputStream ins = Channels.newInputStream(channel);
InputStreamReader is = new InputStreamReader(ins,"utf-8");
BufferedReader in = new BufferedReader(is);
String res = in.readLine();
while (!res.equals("")) {
System.out.println(res);
res = in.readLine();
}
......①
好了,現在我讀完TCP流的一個time.In爲了繼續使用選擇,我應該設置通道阻塞模式爲false。
channel.configureBlocking(false);
的問題是,它結合了渠道和選擇已經canceled.I要註冊mychannel again.What我應該做的關鍵?看來如果我在①上再次使用mychannel.register(selector, SelectionKey.OP_READ)
,它會拋出Exception
。
我的run()方法的代碼如下:
try {
if (selector.select(getTimeout()) != 0) {
Iterator<SelectionKey> it = selector.selectedKeys().iterator();
while (it.hasNext()) {
SelectionKey key = it.next();
if (key.isReadable()) {
SocketChannel channel = (SocketChannel) key.channel();
key.cancel();
channel.configureBlocking(true);
InputStream ins = Channels.newInputStream(channel);
InputStreamReader is = new InputStreamReader(ins,"utf-8");
BufferedReader in = new BufferedReader(is);
String res = in.readLine();
while (!res.equals("")) {
System.out.println("========" + res);
res = in.readLine();
}
channel.configureBlocking(false);
System.out.println(key.isValid());
proxykey=channel.register(selector, SelectionKey.OP_READ);
}
it.remove();
}
}
} catch (IOException ex) {
ex.printStackTrace();
}
它拋出的異常是:
Exception in thread "Thread-0" java.nio.channels.CancelledKeyException
at sun.nio.ch.SelectionKeyImpl.ensureValid(Unknown Source)
at sun.nio.ch.SelectionKeyImpl.interestOps(Unknown Source)
at java.nio.channels.spi.AbstractSelectableChannel.register(Unknown Source)
at java.nio.channels.SelectableChannel.register(Unknown Source)
at AgentThread.run(AgentThread.java:185)
拋出* what * exception? – EJP 2013-03-06 19:53:27
謝謝。我想編輯問題以顯示我的運行方法代碼以及它拋出的異常。 – William 2013-03-07 00:50:33