因此,我最近编写了一个java类,它扩展了异常,并使用该类的一个实例来检查用例,并在发生错误时抛出自己。我发现当main的调用方捕获到这个异常时,它说异常是从创建异常的位置抛出的,而不是从抛出的位置抛出的。我只是想知道这是为什么,以及它是否是jvm的预期行为,因为这不是一种常见的抛出异常的方式。如果它是有意的行为,那么什么是理性的,因为从抛出异常的位置看,行号会更有用(并且可能更容易在堆栈中跟踪)。示例案例随后显示了预期的行为和意外。
正常异常抛出:
1 public class Test
2 {
3 public static void main(String ... args) throws Throwable
4 {
5 switch(5)
6 {
7 case 1: throw new Exception("Exception");
8 case 2: throw new Exception("Exception");
9 case 3: throw new Exception("Exception");
10 case 4: throw new Exception("Exception");
11 case 5: throw new Exception("Exception");
12 }
13 }
14 }产出:
Exception in thread "main" java.lang.Exception: Exception
at Test.main(Test.java:11)我的方法(简化):
1 public class Test
2 {
3 public static void main(String ... args) throws Throwable
4 {
5 Exception e = new Exception("Exception");
6 switch(5)
7 {
8 case 1: throw e;
9 case 2: throw e;
10 case 3: throw e;
11 case 4: throw e;
12 case 5: throw e;
13 }
14 }
15 }产出:
Exception in thread "main" java.lang.Exception: Exception
at Test.main(Test.java:5)发布于 2012-03-31 08:57:03
它说异常抛出的行是从创建异常的位置抛出的,而不是从抛出的位置抛出的。我只是想知道这是为什么,以及它是否是jvm的预期行为
是。这不仅是有意的,而且是有记录的。请参阅java.lang.Throwable的Javadoc:“throwable包含其创建线程时的执行堆栈的快照。”如果您不想这样做,您可以在抛出它之前调用fillInStackTrace()。
发布于 2012-03-31 08:58:22
来自JavaDoc用于Throwable
通常,这是创建和抛出该throwable的点。
这有点模棱两可,但是99%的时间是在抛出异常时创建的。我想,当您考虑重新抛出异常时,从创建点创建堆栈跟踪可能更有意义,例如:
void bar() throws Exception
{
throw Exception();
}
void foo() throws Exception
{
try
{
bar();
}
catch (Exception e)
{
throw e;
}
}
public static void main(String[] args)
{
foo();
}知道异常是在bar()中创建的比知道它是在foo()中重新抛出的更为有用。如果此信息很重要,则可以抛出一个新的异常,将原始异常作为原因参数。
更新
为了说明,如果您真的想知道异常也是在foo()中抛出的,那么您可以在foo()中这样做。
void foo() throws Exception
{
try
{
bar();
}
catch (Exception e)
{
throw new Exception("Some more useful information from foo", e);
}
}https://stackoverflow.com/questions/9954463
复制相似问题