简体   繁体   中英

Is it possible to throw an checked Exception implicitly, without any athrow instruction?

In Java, both checked exception and unchecked exception can be thrown explicitly, ie, by a throw statement. Besides, unchecked exceptions like ArithmeticException and OutOfMemoryError can be triggered without any explicit throw statement like this:

public static void throwArithmeticException() {
    int i = 1;
    int j = i / 0;
}

public static void throwOutOfMemoryError() {
    List<Object> list = new ArrayList<>();
    while(true) {
        list.add(new Object());
    }
}

So my question is, is there any way to trigger an checked Exception, like IOException , implicitly, ie not using any throw statement?

You can do it, but you shouldn't 1 .

I assume that you are talking about the athrow bytecode instruction . (And that you really asking if you can trigger an exception from your code without using a throw statement.)

There are (at least) two ways for an application to throw an arbitrary Java exception (checked or unchecked) that don't involve an explicit athrow instruction.

  1. You can call Unsafe.throwException(Throwable) .

  2. In native code, you can call the Throw or ThrowNew functions in the JNI API.

In both cases, you can circumvent the Java (compile time and verifier) checks that are intended to ensure that checked exceptions are always declared (via a throws clause) or handled.

Note using Unsafe or native code means that your code is not Pure Java. It won't be portable. Furthermore it is easy to do things that will make a JVM unstable. JVM crashes are not unusual.


In addition, the JVM will itself throw exceptions without an athrow instruction. For example, if you try to use new FileInputStream to open a file that doesn't exist and FileNotFoundException is thrown, it is being throw from native code, not from compiled Java code.

It follows that your application can use this mechanism to implicitly throw many checked and unchecked exceptions; eg by deliberately trying to open a non-existent file. However, the method signature for read declares that it may throw IOException , so the compiler knows about this... from the perspective of the checked exception rules.


1 - And if you application design requires this kind of craziness, you would be advised to come up with an alternative. It is a bad idea to try to fight Java's checked exception rules. If you dislike them so much that you are contemplating this, you should pick a different programming language.

In java bytecode, this is only possible for exceptions the JVM can generate itself, but IOException isn't one of them. You can only use the virtual machine to throw a run-time exception which is thrown by interpreting bytecode. For example this code:

aconst_null
monitorexit

will throw a NullPointerException . This is theoretically also possible for throwables like NegativeArraySizeException , IllegalMonitorStateException , WrongMethodTypeException , BootstrapMethodError , IncompatibleClassChangeError and many other. You can find out more here

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM