如何把阻塞输入流包装成非阻塞的?
使用common-net.jar中的TelnetClient来模拟一个telnet客户端登录和执行命令。
TelnetClient.getInputStream()获取的输入流,利用它的read方法读取时是可能陷入等待。ReadInformation.readTelnet()方法获取同步锁时,如果陷入输入流的read等待,整个程序就无法进行下去了。我想把这个输入流包装成非阻塞的,不知道能不能实现?哪位高手有其它的解决方法给指点一二,在这先谢过了!
代码如下:
- Java code
import org.apache.commons.net.telnet.*; import java.io.*; import java.net.SocketException; import java.util.StringTokenizer; public class TmhTelnet implements TelnetNotificationHandler { private static TelnetClient tc = null; private static InputStream instr; private static PrintWriter out; public static void main(String args[]) throws IOException{ TmhTelnet telnet = new TmhTelnet("127.0.0.1",23); ReadInformation readInfo = new ReadInformation("command.txt",instr,out); ReadFileThread rfthread = new ReadFileThread(readInfo); ReadTelnetThead rtthread = new ReadTelnetThead(readInfo); Thread rtt = new Thread(rtthread); rtt.start(); Thread rft = new Thread(rfthread); rft.start(); System.out.println("return"); } public TmhTelnet(String host, int port) { intconnect(host,port); } private boolean intconnect(String host, int port) { try { tc = new TelnetClient(); TerminalTypeOptionHandler ttopt = new TerminalTypeOptionHandler( "VT100", false, false, true, false); EchoOptionHandler echoopt = new EchoOptionHandler(true, false, true, false); SuppressGAOptionHandler gaopt = new SuppressGAOptionHandler(true, true, true, true); tc.addOptionHandler(ttopt); tc.addOptionHandler(echoopt); tc.addOptionHandler(gaopt); tc.connect(host, port); instr = tc.getInputStream(); out = new PrintWriter(tc.getOutputStream()); return true; } catch (Exception e) { e.printStackTrace(); try { tc.disconnect(); } catch (IOException e1) { // TODO Auto-generated catch block e1.printStackTrace(); } return false; } } public void receivedNegotiation(int negotiation_code, int option_code) { String command = null; if (negotiation_code == TelnetNotificationHandler.RECEIVED_DO) { command = "DO"; } else if (negotiation_code == TelnetNotificationHandler.RECEIVED_DONT) { command = "DONT"; } else if (negotiation_code == TelnetNotificationHandler.RECEIVED_WILL) { command = "WILL"; } else if (negotiation_code == TelnetNotificationHandler.RECEIVED_WONT) { command = "WONT"; } System.out.println("Received " + command + " for option code " + option_code); } } - Java code
public class ReadFileThread implements Runnable { private ReadInformation rf = null; public ReadFileThread(ReadInformation rf){ this.rf = rf; } public void run() { while(true){ rf.readFile(); } }}- Java code
public class ReadTelnetThead implements Runnable{ private ReadInformation rf = null; public ReadTelnetThead(ReadInformation rf){ this.rf = rf; } public void run() { while(true){ rf.readTelnet(); } } }
- Java code
import java.io.BufferedReader; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.PrintWriter; import java.nio.ByteBuffer; import java.nio.CharBuffer; import java.nio.charset.Charset; import java.nio.charset.CharsetDecoder; public class ReadInformation { private String filename; private InputStream input; private PrintWriter pw; private BufferedReader readCommand = new BufferedReader(new InputStreamReader(System.in)); private BufferedReader br = null; Integer i = 1; public ReadInformation(String filename,InputStream input,PrintWriter pw) throws FileNotFoundException{ this.filename = filename; this.input = input; this.pw = pw; br = new BufferedReader(new InputStreamReader(new FileInputStream(filename))); } public synchronized void readFile(){ try { String line = br.readLine(); if(i%2==1) this.wait(); if(line!=null&&!"".equals(line)){ pw.println(line); pw.flush(); System.out.println(line); System.out.println("*******************"); } else{ line=readCommand.readLine(); if(line==null ||"".equals(line)){ pw.println("\r\n"); pw.flush(); System.out.println("输入指定为空,请输入指令。"); } else{ pw.println(line); pw.flush(); System.out.println(line); System.out.println("*******************"); } } Thread.sleep(100); i++; this.notify(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } public synchronized void readTelnet(){ try { byte[] buff = new byte[4096]; int ret_read = 0; if(i%2==0) this.wait(); if((ret_read=input.read(buff)) >= 0) { if (ret_read > 0) { Charset charset = Charset.forName("GB18030"); //创建解码器(CharsetDecoder)对象 CharsetDecoder decoder = charset.newDecoder(); //使用解码器将ByteBuffer转换成CharBuffer ByteBuffer by = ByteBuffer.allocate(4096); by.put(buff,0,ret_read); by.limit(by.position()); by.position(0); CharBuffer charBuffer = decoder.decode(by); System.out.print(charBuffer); System.out.println("##################"); } } this.notify(); i++; } catch (Exception e) { System.err.println("Exception while reading socket:" + e.getMessage()); } } }command.txt:
administrator
123
[解决办法]
我不是很明白你的需求,如果你想把阻塞变成非阻塞,那么你想读到些什么呢?
如果你只是程序没办法跑下去,那么用线程就可以了啊。
[解决办法]
[color=#99CC00][/color]
[color=#FFFFFF].[/color]