Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/google-apps-script/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 检测写入标准错误流_Java_Multithreading_Exception_Exception Handling_Stderr - Fatal编程技术网

Java 检测写入标准错误流

Java 检测写入标准错误流,java,multithreading,exception,exception-handling,stderr,Java,Multithreading,Exception,Exception Handling,Stderr,是否没有办法(不管它有多“黑”)检测Java何时被写入,以便在发生这种情况时能够执行逻辑我目前正在使用Thread(我们称之为snowningthread)的一个自定义子类,它以类似于以下代码的方式在其实现中吞咽了大量异常: public final class SwallowingThread extends Thread { ... @Override public void run() { ServerSocket socket = new Se

是否没有办法(不管它有多“黑”)检测Java何时被写入,以便在发生这种情况时能够执行逻辑我目前正在使用
Thread
(我们称之为
snowningthread
)的一个自定义子类,它以类似于以下代码的方式在其实现中吞咽了大量异常:

public final class SwallowingThread extends Thread {

    ...

    @Override
    public void run() {
        ServerSocket socket = new ServerSocket(80, 100);
        try {
            Socket connected = socket.accept();
            // Do stuff with socket here
        } catch (UnknownHostException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}
然而,在我的代码中,我希望能够处理在使用
吞咽线程
实例时发生的
未知后异常
IOException
;发生此捕获和打印错误后,是否无法检测到该错误我最初尝试编写一个函数来执行此操作,结果发现它没有捕获异常,因为它们被吞没了,而不是简单地被包装在一个
RuntimeException
中并向前抛出


当然,解决这个问题的“更好”方法是重新编写类的逻辑,但是没有快速而肮脏的方法来解决这个问题,而不必触摸
吞咽线程

您可以实现自己的类(我称之为DelegatingErrorPrintStream),该类派生自PrintStream,它会通知您是否有新的输出,然后委托给System.err 现在,您可以使用将DelegatingErrorPrintStream设置为System.err的输出流 系统设置错误(err)

完整示例包括用法:

import java.io.FileNotFoundException;
import java.io.PrintStream;
import java.io.UnsupportedEncodingException;

public class ErrorNotifierExample {
private static final class ErrorDelegatingPrintStream extends PrintStream {
    public ErrorDelegatingPrintStream(PrintStream defaultErr)
            throws FileNotFoundException, UnsupportedEncodingException {
        super(defaultErr);
    }

    @Override
    public void print(boolean b) {
        super.print(b);
        notifyListener(b);
    }

    @Override
    public void print(char c) {
        super.print(c);
        notifyListener(c);
    }

    @Override
    public void print(int i) {
        super.print(i);
        notifyListener(i);
    }

    @Override
    public void print(long l) {
        super.print(l);
        notifyListener(l);
    }

    @Override
    public void print(float f) {
        super.print(f);
        notifyListener(f);
    }

    @Override
    public void print(double d) {
        super.print(d);
        notifyListener(d);
    }

    @Override
    public void print(char[] s) {
        super.print(s);
        notifyListener(s);
    }

    @Override
    public void print(String s) {
        super.print(s);
        notifyListener(s);

    }

    @Override
    public void print(Object obj) {
        super.print(obj);
        notifyListener(obj);

    }

    @Override
    public PrintStream append(CharSequence csq, int start, int end) {
        notifyListener(csq); // TODO will need some special handling
        return super.append(csq, start, end);
    }

    private void notifyListener(Object string) {
        // TODO implement your handling here. System.out printing is just an
        // example.
        System.out.println(String.valueOf(string));
    }
}

public static void main(String[] args) throws FileNotFoundException, UnsupportedEncodingException {
    ErrorDelegatingPrintStream errReplacement = new ErrorDelegatingPrintStream(System.err);
    System.setErr(errReplacement);

    System.err.println("TEST01");
    throw new RuntimeException("just a test output for ERROR handling");
}
}

正如一些人已经建议的那样,您可以使用定制的
PrintStream

它将替换标准错误流,但也封装它并在需要时调用它

由于您感兴趣的是异常和堆栈跟踪,所以覆盖
print(String)
应该足够了(
println(String)
已经调用了这个方法+
newLine()

这条溪流可能是这样的:

import java.io.PrintStream;

public class CustomPrintStream extends PrintStream {


    public CustomPrintStream(final PrintStream out) {

        super(out);

    }

    @Override
    public void print(final String s) {

        super.print(s);
        // some String is written to the error stream, Do something !

    }

}
您可以这样使用它,在应用程序开始时,只需调用

System.setErr(new CustomPrintStream(System.err));

您可以创建一个包装
系统的
PrintStream
System.setErr(新的MyDelegatingPrintStream(System.err))可能重复@MuratK,不,我不想简单地把输入到stderr的数据放到另一个地方:我想能够执行一些逻辑一次/如果这个数据被写入stderr。所有这些答案都很好,但这几乎就是我最终做的(特别是通过将
使用者
作为委托传递,以代替
notifyListener(对象)
逻辑)。