0

I'm developing a library and in some method I want to throw a ClassNotFoundException but eclipse force me to either 'Add a throws declaration' or 'Surround with try/catch'. I do not want to implement any of them, what I want is to throw this excepcion to the client of the class. I've seen that all classes that extend ReflectiveOperationException force me to add or surround the exception. In the other hand I've seen that classes that extend RuntimeException does not require to add or surround the exception.

As an abstraction of my problem, imagine a code like this:

public Class getClassForCellType(int cellTypeRequested) {

        Class cellClassRequired = null;

        if (cellTypeRequested == 0) {
            cellClassRequired = CellA.class;
        } else if (cellTypeRequested == 1) {
            cellClassRequired = CellB.class;
        } else {
            throw new ClassNotFoundException("cellType Not Available");
        }

        return cellClassRequired;
    }

I want to throw ClassNotFoundException because is what is happening and I would not like to use another more generic class. Someone could please explain me why those ReflectiveOperationException classes require handling them directly.

Androider
  • 441
  • 2
  • 6
  • 17
  • 7
    [Java: checked vs unchecked exception explanation](http://stackoverflow.com/questions/6115896/java-checked-vs-unchecked-exception-explanation) – Sotirios Delimanolis Oct 20 '14 at 16:37
  • 1
    Have you ever heard of the term "checked exception"? It is a notorious aspect of the Java language. – Marko Topolnik Oct 20 '14 at 16:37
  • Adding a `throws` declaration isn't really "implementing" anything; it's more of a signal to clients that call this method that this exception could be thrown, and that they either need to catch it or declarer that they also throw it. This is probably what you want to do. – ajb Oct 20 '14 at 16:43

4 Answers4

2

Eclipse is telling you (as any Java compiler must do) that if you want a ClassNotFoundException to be able to escape your method, the method must declare that that is a possibility, like so:

public Class getClassForCellType(int cellTypeRequested) throws ClassNotFoundException {
    // ...
        throw new ClassNotFoundException("cellType Not Available");
    // ...
    return cellClassRequired;
}

This is the rule for any Exception other than java.lang.RuntimeException and its subclasses.

John Bollinger
  • 160,171
  • 8
  • 81
  • 157
  • I think Error is subclass of Throwable for which your last statement does not stand true. Instead of Throwable, it is Exception class I beleive, for which RuntimeException is exceptional of the rule. +1 , because it answer the question though. – Jimmy Oct 20 '14 at 16:55
  • Quite right, @Jimmy. I typed too fast. Now corrected. – John Bollinger Oct 20 '14 at 17:03
2

I think your problem arises because you are not using ClassNotFoundException for the purpose it is intended. This exception is very specifically intended to be thrown when the implementation of a requested Java class is not available on the classpath.

Here you are trying to translate a parameter into a Class, but that is not the same as the system level error of a missing Class definition.

I would create your own CellTypeClassNotResolvedException which extends RuntimeException and throw that instead:

public CellTypeClassNotResolvedException extends RuntimeException {
    public CellTypeClassNotResolvedException(String s) {
        super(s);
    }
}
BarrySW19
  • 3,759
  • 12
  • 26
0

You need to add a throws declaration due to ClassNotFoundException being a checked exception. TO fix your code, it would look like this:

public Class getClassForCellType(int cellTypeRequested) throws ClassNotFoundException {

    Class cellClassRequired = null;

    if (cellTypeRequested == 0) {
        cellClassRequired = CellA.class;
    } else if (cellTypeRequested == 1) {
        cellClassRequired = CellB.class;
    } else {
        throw new ClassNotFoundException("cellType Not Available");
    }

    return cellClassRequired;
}
Community
  • 1
  • 1
Pokechu22
  • 4,984
  • 9
  • 37
  • 62
0

In Java, we have two core types of exceptions: Checked, and unchecked exceptions.

Checked exceptions: If this type of exception is thrown, it has to be explicitly handled by either the client of the method or the method itself. ReflectiveOperationException is an example of this. These types of exceptions are usually used to reflect API problems, usage problems, legitimate/business application failures.

Java's way of fulfilling this requirement is to say you either have to handle (i.e. catch the exception) in your method, or you have to explicitly inform the client that they may get this exception (i.e. throws clause).

Unchecked exceptions: If this type of exception is thrown, it does not have to be handled explicitly. These are usually reflective of programming errors - for instance, ArrayIndexOutOfBoundsExceptions is a good example - you wouldn't anticipate running into this problem, and if you did, you can be relatively confident it's a bug and don't expect the client to cater for it in their code!


In your example, you are trying to tell the client that they passed you a bad parameter by throwing the ClassNotFoundException. They need to know this might be thrown in order to handle the scenario in their code, hence you need to add the throws declaration to the method signature.

public Class getClassForCellType(int cellTypeRequested) throws ClassNotFoundException {

}

See Oracle Docs on more exception tutorials: http://docs.oracle.com/javase/tutorial/essential/exceptions/index.html

Gembles
  • 21
  • 1