當我使用System.out.println
打印出我的日誌消息時,我正在編寫一個基本的服務器程序。我寫了一個基本的類文件,用它來寫出日誌。如果我寫:Java PrintStream重定向意外行爲
System.out.println("Hello, world!");
System.out.println("Goodbye, world");
所需的輸出將是:
Log message - Hello, world!
Log message - Goodbye, world!
結束意外事件發生不匹配所需的輸出。相反,它輸出到以下內容。
Log message - Hello, world!
Goodbye, world!
主方法的代碼:
public static void main(String[] args){
LogManager.start();
System.out.println("Hello, world!");
System.out.println("Goodbye, world!");
LogManager.stop();
}
類LogManager的切換即打印出來到默認PrintStream
,並保持舊的拷貝打印出日誌消息。但是,「日誌消息 - 」並不總是以前綴爲前綴。雖然在每次呼叫println
之間睡眠2000毫秒時,輸出如下所示。
Log message - Hello, world!
Log message - Goodbye, world!Log message -
LogManager的代碼如下。
import java.io.ByteArrayOutputStream;
import java.io.OutputStream;
import java.io.PrintStream;
public class LogManager implements Runnable{
private final PrintStream ps;
private final OutputStream out;
private static boolean cont = true;
public static void start(){
OutputStream stdout = new ByteArrayOutputStream();
PrintStream ps = new PrintStream(stdout);
Thread th = new Thread(new LogManager(System.out, stdout));
System.setOut(ps);
th.start();
}
public static void stop(){
cont = false;
}
public LogManager(PrintStream std, OutputStream out){
this.ps = std;
this.out = out;
}
@Override
public void run() {
ByteArrayOutputStream baos = (ByteArrayOutputStream) out;
while(true){
if(!cont) return;
byte[] bytes = baos.toByteArray();
if(bytes.length > 0){
baos.reset();
ps.print("Log message - " + new String(bytes));
}
}
}
}
有人請指點我做錯了什麼,非常感謝幫助。我希望遠離圖書館,因爲我希望將JAR的大小保持在最低限度,並且不需要包含額外的軟件包,但主要是爲了知道我沒有使用任何其他軟件庫來實現我正在做的事情。
我試過了,但它似乎產生相同的結果。前綴僅添加到某些日誌中。我相信這可能與緩衝有關。我做了'cont' volatile,並且將循環中的代碼切換到了您所顯示的代碼,但它似乎仍然執行相同的操作。 – Garhoogin
@Garhoogin更新 – yshavit