I have encountered that I must catch all checked exceptions inside stream expresions. I have read very popular topic:
How can I throw CHECKED exceptions from inside Java 8 streams?
And there is answer which suugest following approach:
we have 3 strings:
"java.lang.Object"
"java.lang.Integer"
"java.lang.Strin"
We want to load classes by name.
Thus we need to use Class#forName method
Class#forName java doc)
As you can see following method declaration contains
throws ClassNotFoundException
Thus if we use usual loop we need to write followig code:
public void foo() throws ClassNotFoundException {
    String arr[] = new String[]{"java.lang.Object", "java.lang.Integer", "java.lang.Strin"};
    for(String className:arr){
        Class.forName(className);
    }
}
lets try to rewrite it using streams:
 public void foo() throws ClassNotFoundException {
        String arr[] = new String[]{"java.lang.Object", "java.lang.Integer", "java.lang.Strin"};
        Stream.of(arr).forEach(Class::forName);
    }
compiler says that:
Error:(46, 32) java: incompatible thrown types java.lang.ClassNotFoundException in method reference
Ok, lets try to use approach from topic mentioned above:
we create following methods:
public static <T, E extends Exception> Consumer<T> rethrowConsumer(Consumer_WithExceptions<T, E> consumer) {
    return t -> {
        try {
            consumer.accept(t);
        } catch (Exception exception) {
            throwAsUnchecked(exception);
        }
    };
}
 @FunctionalInterface
 public interface Consumer_WithExceptions<T, E extends Exception> {
     void accept(T t) throws E;
 }
@SuppressWarnings("unchecked")
private static <E extends Throwable> void throwAsUnchecked(Exception exception) throws E {
    throw (E) exception;
}
And client code will looks like this:
public void foo() throws ClassNotFoundException {
        String arr[] = new String[]{"java.lang.Object", "java.lang.Integer", "java.lang.Strin"};
        Stream.of(arr).forEach(rethrowConsumer(Class::forName));
    }
I want to know how does it work. It is really unclear for me.
lets research rethrowConsumer:
public static <T, E extends Exception> Consumer<T> rethrowConsumer(Consumer_WithExceptions<T, E> consumer) {
    return t -> {
        try {
            consumer.accept(t);
        } catch (Exception exception) {
            throwAsUnchecked(exception);
        }
    };
}
and throwAsUnchecked signature look slike
private static <E extends Throwable> void throwAsUnchecked(Exception exception) throws E {
Please clarify this mess.
P.S.
I localized that magic happens inside throwAsUnchecked because following snippet correct
   public static <T, E extends Exception> Consumer<T> rethrowConsumer(Consumer_WithExceptions<T, E> consumer) {
        return t -> {
            try {
                throw new Exception();
            } catch (Exception exception) {
                throwAsUnchecked(exception);
            }
        };
    }
But following not
public static <T, E extends Exception> Consumer<T> rethrowConsumer(Consumer_WithExceptions<T, E> consumer) {
    return t -> {
        try {
            consumer.accept(t);
        } catch (Exception exception) {
            throw new Exception();
            //throwAsUnchecked(exception);
        }
    };
}
 
     
    