간과하기 쉬운 이상 문제
public class Throwable implements Serializable {
/** use serialVersionUID from JDK 1.0.2 for interoperability */
private static final long serialVersionUID = -3042686055658047285L;
/**
* Native code saves some indication of the stack backtrace in this slot.
*/
private transient Object backtrace;
/**
* Specific details about the Throwable. For example, for
* {@code FileNotFoundException}, this contains the name of
* the file that could not be found.
*
* @serial
*/
private String detailMessage;
/**
* Holder class to defer initializing sentinel objects only used
* for serialization.
*/
private static class SentinelHolder {
/**
* {@linkplain #setStackTrace(StackTraceElement[]) Setting the
* stack trace} to a one-element array containing this sentinel
* value indicates future attempts to set the stack trace will be
* ignored. The sentinal is equal to the result of calling:<br>
* {@code new StackTraceElement("", "", null, Integer.MIN_VALUE)}
*/
public static final StackTraceElement STACK_TRACE_ELEMENT_SENTINEL =
new StackTraceElement("", "", null, Integer.MIN_VALUE);
/**
* Sentinel value used in the serial form to indicate an immutable
* stack trace.
*/
public static final StackTraceElement[] STACK_TRACE_SENTINEL =
new StackTraceElement[] {STACK_TRACE_ELEMENT_SENTINEL};
}
/**
* A shared value for an empty stack.
*/
private static final StackTraceElement[] UNASSIGNED_STACK = new StackTraceElement[0];
/*
* To allow Throwable objects to be made immutable and safely
* reused by the JVM, such as OutOfMemoryErrors, fields of
* Throwable that are writable in response to user actions, cause,
* stackTrace, and suppressedExceptions obey the following
* protocol:
*
* 1) The fields are initialized to a non-null sentinel value
* which indicates the value has logically not been set.
*
* 2) Writing a null to the field indicates further writes
* are forbidden
*
* 3) The sentinel value may be replaced with another non-null
* value.
*
* For example, implementations of the HotSpot JVM have
* preallocated OutOfMemoryError objects to provide for better
* diagnosability of that situation. These objects are created
* without calling the constructor for that class and the fields
* in question are initialized to null. To support this
* capability, any new fields added to Throwable that require
* being initialized to a non-null value require a coordinated JVM
* change.
*/
/**
* The throwable that caused this throwable to get thrown, or null if this
* throwable was not caused by another throwable, or if the causative
* throwable is unknown. If this field is equal to this throwable itself,
* it indicates that the cause of this throwable has not yet been
* initialized.
*
* @serial
* @since 1.4
*/
private Throwable cause = this;
/**
* The stack trace, as returned by {@link #getStackTrace()}.
*
* The field is initialized to a zero-length array. A {@code
* null} value of this field indicates subsequent calls to {@link
* #setStackTrace(StackTraceElement[])} and {@link
* #fillInStackTrace()} will be be no-ops.
*
* @serial
* @since 1.4
*/
private StackTraceElement[] stackTrace = UNASSIGNED_STACK;
2 전역 이상, 프로젝트에서 같은 이상을 사용할 때 전역 이상으로 설정합니다.다음과 같습니다.
public class TestException extends RuntimeException {
/**
*
*/
public static TestException GLOBAL_EXCEPTION =new TestException("GLOBAL_EXCEPTION");
/**
*
*/
private static final long serialVersionUID = -6631291006030705175L;
public TestException(String string){
super(string);
}
}
3 다중 스레드 인쇄 시 이상 스택 정보의 혼란을 초래할 수 있습니다.
public class ExceptionTest {
static final Logger LOG = LoggerFactory.getLogger(ExceptionTest.class);
public static void main(String args[]){
Thread threadOne = new Thread("one"){
@Override
public void run() {
super.run();
for(;;){
try{
throwByOne();
}catch (Exception e){
LOG.debug(" :", e);
}
}
}
};
Thread threadTwo = new Thread("two"){
@Override
public void run() {
super.run();
for(;;){
try{
throwByTwo();
}catch (Exception e){
LOG.debug(" :", e);
}
}
}
};
threadOne.start();
threadTwo.start();
try {
Thread.sleep(99999L);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public static void throwByOne() throws Exception {
try{
System.out.println(throwByOne1());
}catch(Exception e){
throw e;
}
}
public static int throwByOne1() throws Exception{
try{
return 1/0;
}catch(Exception e){
throw TestException.GLOBAL_EXCEPTION;
}
}
public static void throwByTwo() throws Exception{
try{
System.out.println(throwByTwo2());
}catch(Exception e){
throw e;
}
}
public static int throwByTwo2() throws Exception{
try{
return 2/0;
}catch(Exception e){
throw TestException.GLOBAL_EXCEPTION;
}
}
}
4 출력: 2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.?-two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.086 [one] DEBUG ExceptionTest.? - one
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [one] DEBUG ExceptionTest.? - one
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [one] DEBUG ExceptionTest.? - one
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [one] DEBUG ExceptionTest.? - one
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [one] DEBUG ExceptionTest.? - one
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [one] DEBUG ExceptionTest.? - one
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [one] DEBUG ExceptionTest.? - one
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [one] DEBUG ExceptionTest.? - one
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOne(ExceptionTest.java:51) ~[bin/:na]
at ExceptionTest$1.run(ExceptionTest.java:20) ~[bin/:na]
2015-07-30 22:47:44.087 [two] DEBUG ExceptionTest.? - two
TestException: GLOBAL_EXCEPTION
at TestException.
at ExceptionTest.throwByOne1(ExceptionTest.java:60) ~[bin/:na]
at ExceptionTest.throwByOn