Throwable 源码阅读

Throwable

  • 属性说明
/**
 *  Java 语言中所有错误和异常的基类,此类及其子类才能通过 throws 被 JVM 虚拟机抛出。
 * @since 1.0
 */
public class Throwable implements Serializable {
    /** use serialVersionUID from JDK 1.0.2 for interoperability */
    private static final long serialVersionUID = -3042686055658047285L;

    /**
     *  JVM 会保存一些栈回溯信息到此对象上
     */
    private transient Object backtrace;

    /**
     *  异常的细节信息
     */
    private String detailMessage;

    /**
     *  共享的空堆栈信息
     */
    private static final StackTraceElement[] UNASSIGNED_STACK = new StackTraceElement[0];

    /**
     *  引起此 Throwable 抛出的源 Throwable 对象
     * @since 1.4
     */
    private Throwable cause = this;

    /**
     *  此 Throwable 关联的堆栈信息
     * @serial
     * @since 1.4
     */
    private StackTraceElement[] stackTrace = UNASSIGNED_STACK;

    /**
     *  栈回溯的深度
     */
    private transient int depth;

    // Setting this static field introduces an acceptable
    // initialization dependency on a few java.util classes.
    private static final List<Throwable> SUPPRESSED_SENTINEL = Collections.emptyList();

    /**
     *  被抑制的异常对象列表
     * @serial
     * @since 1.7
     */
    private List<Throwable> suppressedExceptions = SUPPRESSED_SENTINEL;

    /** 用于抑制空指针异常的消息 */
    private static final String NULL_CAUSE_MESSAGE = "Cannot suppress a null exception.";

    /** Message for trying to suppress oneself. */
    private static final String SELF_SUPPRESSION_MESSAGE = "Self-suppression not permitted";

    /** 导致异常堆栈跟踪的标题信息 */
    private static final String CAUSE_CAPTION = "Caused by: ";

    /** 被抑制的异常堆栈跟踪的标题信息 */
    private static final String SUPPRESSED_CAPTION = "Suppressed: ";
  • 实例化
    /**
     *  创建一个无描述信息的 Throwable 对象
     */
    public Throwable() {
        fillInStackTrace();
    }

    /**
     *  创建一个持有指定描述信息 message 的 Throwable 对象
     * @param   message 详细的信息
     */
    public Throwable(String message) {
        fillInStackTrace();
        detailMessage = message;
    }

    /**
     *  创建一个持有详细信息和异常来源的 Throwable 对象
     * @param  message  详细描述信息
     * @param  cause    引起此 Throwable 的源 Throwable 对象
     * @since  1.4
     */
    public Throwable(String message, Throwable cause) {
        fillInStackTrace();
        detailMessage = message;
        this.cause = cause;
    }

    /**
     *  创建一个持有源 Throwable 实例的 Throwable 对象
     *
     * @param  cause    源 Throwable 对象
     * @since  1.4
     */
    public Throwable(Throwable cause) {
        fillInStackTrace();
        detailMessage = cause==null ? null : cause.toString();
        this.cause = cause;
    }

    /**
     *  填充此 Throwable 实例的堆栈跟踪信息
     */
    public synchronized Throwable fillInStackTrace() {
        if (stackTrace != null ||
                backtrace != null /* Out of protocol state */ ) {
            fillInStackTrace(0);
            stackTrace = UNASSIGNED_STACK;
        }
        return this;
    }

    private native Throwable fillInStackTrace(int dummy);
  • 打印异常堆栈
    /**
     *  将异常堆栈信息输出到标准错误流
     */
    public void printStackTrace() {
        printStackTrace(System.err);
    }

    /**
     *  将此 Throwable 的堆栈信息输出到指定的 PrintStream s 中
     *
     * @param s 用于输出的目标 {@code PrintStream}
     */
    public void printStackTrace(PrintStream s) {
        printStackTrace(new WrappedPrintStream(s));
    }

    private void printStackTrace(PrintStreamOrWriter s) {
        final Set<Throwable> dejaVu = Collections.newSetFromMap(new IdentityHashMap<>());
        dejaVu.add(this);

        synchronized (s.lock()) {
            // 打印此 Throwable 的信息
            s.println(this);
            // 打印相关的堆栈信息
            final StackTraceElement[] trace = getOurStackTrace();
            for (final StackTraceElement traceElement : trace) {
                s.println("\tat " + traceElement);
            }

            // 打印抑制的异常信息
            for (final Throwable se : getSuppressed()) {
                se.printEnclosedStackTrace(s, trace, SUPPRESSED_CAPTION, "\t", dejaVu);
            }

            // 打印异常原因
            final Throwable ourCause = getCause();
            if (ourCause != null) {
                ourCause.printEnclosedStackTrace(s, trace, CAUSE_CAPTION, "", dejaVu);
            }
        }
    }

    /**
     *  将此 Throwable 的堆栈信息打印到 PrintWriter s 中
     *
     * @param s 用于输出的 {@code PrintWriter}
     * @since   1.1
     */
    public void printStackTrace(PrintWriter s) {
        printStackTrace(new WrappedPrintWriter(s));
    }

    /**
     *  封装 PrintStream and PrintWriter
     */
    private abstract static class PrintStreamOrWriter {
        /** Returns the object to be locked when using this StreamOrWriter */
        abstract Object lock();

        /** Prints the specified string as a line on this StreamOrWriter */
        abstract void println(Object o);
    }

    private static class WrappedPrintStream extends PrintStreamOrWriter {
        private final PrintStream printStream;

        WrappedPrintStream(PrintStream printStream) {
            this.printStream = printStream;
        }

        @Override
        Object lock() {
            return printStream;
        }

        @Override
        void println(Object o) {
            printStream.println(o);
        }
    }

    private static class WrappedPrintWriter extends PrintStreamOrWriter {
        private final PrintWriter printWriter;

        WrappedPrintWriter(PrintWriter printWriter) {
            this.printWriter = printWriter;
        }

        @Override
        Object lock() {
            return printWriter;
        }

        @Override
        void println(Object o) {
            printWriter.println(o);
        }
    }

猜你喜欢

转载自www.cnblogs.com/zhuxudong/p/10504583.html