Posted on 2007-01-14 23:05
網路冷眼@BlogJava 閱讀(4250)
評論(8) 編輯 收藏 所屬分類:
Java 、
Java SE
幾乎所有的Java 集成開發環境都需要調用外部進程進行Java程序的構建,編譯,運行和調試,Eclipse,NetBeans,JBuilder和Intellij IDLE概莫例外。在執行過程中,將提示信息以黑色全部打印在控制臺里,將異常和錯誤以紅色方式打印。以非常醒目交互體驗讓程序員遠離枯燥和乏味。
現在讓我們以Eclipse為例來看看它如何工作的,以揭開它神秘面紗,探究隱藏在后面的秘密。
首先,我們準備一個Java 程序,程序如下所示:
import
java.io.BufferedReader;
import
java.io.IOException;
import
java.io.InputStreamReader;
/**
*
*
@author
lewhwa
*/
public
class
HelloWorld {
public
static
void
main(String[] args)
throws
IOException {
System.out.println(
"
Where will you go to?
"
);
InputStreamReader isr
=
new
InputStreamReader(System.in);
BufferedReader reader
=
new
BufferedReader(isr);
String name
=
reader.readLine();
if
(name.toUpperCase().equals(
"
HEAVEN
"
)) {
System.out.println(
"
Welcome to heaven!
"
);
}
if
(name.toUpperCase().equals(
"
HELL
"
)){
System.err.println(
"
Go away!here is hell
"
);
}
}
}
當運行程序等待輸入時,當輸入為“heaven”時。在Eclipse的控制臺輸出如圖1所示:
圖1
看來,在Eclipse控制臺的標準輸出(stdout,System.out)在控制臺中的顯示為為黑色;標準輸入(stdin,System.in)的顯示為綠色。那么,標準錯誤輸出是咋樣的呢?
再次運行程序,當輸入為“Hell”時。在Eclipse的控制臺輸出如圖2所示:
圖2
哦,標準錯誤輸出(stderr,System.err)在Eclipse的控制臺輸出為綠色。
我們知道,在Linux的Shell或者在Windows的Command Prompt窗口執行程序,可以在屏幕上打印stdin,stdout,stderr的消息。在Windows上執行時,將彈出一個Command Prompt窗口。在VC下寫過Console程序的應該知道,VC在執行這些程序時,也馬上彈出一個這樣的窗口。如果程序執行太快,將一閃而過。可是在諸如Eclipse之類的Java IDE里面,并沒有彈出這樣的窗口。我們禁不住要問,它們應用了什么技巧?
無論VC,還是像Eclipse這樣的IDE,執行程序,實際上是在自己的進程里產生了另外一個子進程,這點誰也比誰強不了多少。但是,VC是直接將運行的console程序直接產生一個Command Prompt窗口。其輸入和輸出均放置到那個窗口里。而Eclipse則將這些輸入和輸出重定向到了自己的Console里。原來一直在像,Eclipse一定采用了什么動態鏈接庫之類的東東來做這些。
直到有一天使用NetBeans,它完全使用Java,是純Java的。作為IDE,也是將Console程序的輸入和輸出均在IDE 自己Console顯示。這樣,我才明白,一定在Java API里有這樣的功能:能將外部程序的輸入和輸出進行攔截,然后在重定向到其它的地方。
重新梳理了一下思路,原來使用過Runtime.exec()這樣的東東,是否所有的一切與之有關呢?但只是打開Notepad查看一下某個文本文件之類的應用,搞定也就pass了,沒有深究。
仔細查了查這個類,終于發現了這個秘密。秘密就在Process這個類。Runtime.getRuntime.exec()執行外部程序后,將返回一個Process對象。Process有三個函數與此有關:
getInputStream();
getErrorStream();
getOutputStream();
到此,我們大概已經知道Process是Java IDE完成輸出輸入流攔截的關鍵所在。下篇,我們將利用此技術在自己的應用中實現這種技術。