// Path: src/main/java/ch/codebulb/lambdaomega/L.java
// public static <T> L<T> l() {
//     return new L<>(new ArrayList<>());
// }
// 
// Path: src/main/java/ch/codebulb/lambdaomega/U.java
// public class U {
//     private U() {}
//     
//     /**
//      * Prints the object provided to the standard output.
//      */
//     public static void println(Object out) {
//         System.out.println(out);
//     }
//     
//     /**
//      * Creates a {@link Choice}.
//      */
//     public static <T> Choice<T> Choose(boolean predicate, Supplier<T> function) {
//         return new Choice<>(predicate, function);
//     }
//     
//     /**
//      * Returns <code>true</code> if the <code>predicate</code> provided is <code>true</code> for at least one of the <code>candidates</code>.
//      */
//     public static <T> boolean any(Predicate<T> predicate, T... candidates) {
//         return C.toStream(candidates).anyMatch(predicate);
//     }
//     
//     /**
//      * Represents a simple choice tree. This structure can be used as an alternative to
//      * an <code>if</code> / <code>else if</code> / <code>else</code> structure with optionally enforced choice.<p/>
//      * 
//      * The constructor of this class is not visible; use the convenience {@link U#Choose(boolean, Supplier)} method to create a new instance of this class.
//      * It's best practice to statically import this function in client code.
//      *
//      * @param <T> the return type
//      */
//     public static class Choice<T> {
//         private final L<V2<Boolean, Supplier<T>>> choices;
//         
//         Choice(boolean predicate, Supplier<T> function) {
//             choices = l(v(predicate, function));
//         }
//         
//         /**
//          * Adds an "or" joined option.
//          */
//         public Choice<T> Or(boolean predicate, Supplier<T> function) {
//             choices.a(v(predicate, function));
//             return this;
//         }
//         
//         /**
//          * Returns the result of the first "or" option which evaluates to <code>true</code> or the default value provided if there is no valid option.
//          */
//         public T or(T defaultValue) {
//             V2<Boolean, Supplier<T>> choice = choices.find(it -> it.get0() == true);
//             return choice != null ? choice.get1().get() : defaultValue;
//         }
//         
//         /**
//          * Returns the result of the first "or" option which evaluates to <code>true</code> or <code>null</code> if there is no valid option.
//          */
//         public T orNull() {
//             return or(null);
//         }
//         
//         /**
//          * Returns the result of the first "or" option which evaluates to <code>true</code> or throws a {@link NoValidChoiceException} if there is no valid option.
//          */
//         public T orThrow() throws NoValidChoiceException {
//             V2<Boolean, Supplier<T>> choice = choices.find(it -> it.get0() == true);
//             if (choice != null) {
//                 return choice.get1().get();
//             }
//             else {
//                 throw new NoValidChoiceException();
//             }
//         }
//         
//         /**
//          * Signals that none of the {@link Choice}s provided resolved to <code>true</code>.
//          */
//         public static class NoValidChoiceException extends Exception {
//             
//         }
//     }
// }
// 
// Path: src/main/java/ch/codebulb/lambdaomega/abstractions/OmegaObject.java
// public abstract class OmegaObject {
//     /**
//      * Prints itself to the standard output.
//      */
//     public void println() {
//         U.println(this);
//     }
// }


import static ch.codebulb.lambdaomega.L.l;
import static ch.codebulb.lambdaomega.U.*;
import ch.codebulb.lambdaomega.abstractions.OmegaObject;
import java.util.List;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CompletionStage;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executor;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;
import java.util.function.BiConsumer;
import java.util.function.BiFunction;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;
            public CompletionStage<U> apply(T t) {
                return fn.apply(t).wrapped;
            }
        };
    }
    
    /**
     * @see #then(Function, boolean, Executor)
     */
    public <U> Promise<U> then(Function<? super T, ? extends Promise<U>> fn, boolean async) {
        return then(fn, async, null);
    }
    
    /**
     * @see #then(Function, boolean, Executor)
     */
    public <U> Promise<U> then(Function<? super T, ? extends Promise<U>> fn) {
        return then(fn, false);
    }
    
    /**
     * Like {@link CompletableFuture#allOf(CompletableFuture...)}, but includes a bugfix for the problem described 
     * <a href="http://www.codebulb.ch/2015/07/completablefuture-clean-callbacks-with-java-8s-promises-part-4.html#advanced">here</a>:
     * "Unfortunately, the resulting combined promise is of type <code>&lt;{@link Void}&gt;</code>, leading to the ridiculous need to create a 
     * listener which takes a single parameter of type {@link Void}. Typically, we would much rather like to have a resulting 
     * promise working with the collected results of the combined promises, i.e. of Type <code>&lt;List&lt;�&gt;&gt;</code>."
     * This problem is fixed in this implementation.
     */
    public static <T> Promise<List<T>> allOf(Promise<T>... cfs) {
        Promise<Void> allDoneFuture = new Promise<>(
// Path: src/main/java/ch/codebulb/lambdaomega/L.java
// public static <T> L<T> l() {
//     return new L<>(new ArrayList<>());
// }
// 
// Path: src/main/java/ch/codebulb/lambdaomega/U.java
// public class U {
//     private U() {}
//     
//     /**
//      * Prints the object provided to the standard output.
//      */
//     public static void println(Object out) {
//         System.out.println(out);
//     }
//     
//     /**
//      * Creates a {@link Choice}.
//      */
//     public static <T> Choice<T> Choose(boolean predicate, Supplier<T> function) {
//         return new Choice<>(predicate, function);
//     }
//     
//     /**
//      * Returns <code>true</code> if the <code>predicate</code> provided is <code>true</code> for at least one of the <code>candidates</code>.
//      */
//     public static <T> boolean any(Predicate<T> predicate, T... candidates) {
//         return C.toStream(candidates).anyMatch(predicate);
//     }
//     
//     /**
//      * Represents a simple choice tree. This structure can be used as an alternative to
//      * an <code>if</code> / <code>else if</code> / <code>else</code> structure with optionally enforced choice.<p/>
//      * 
//      * The constructor of this class is not visible; use the convenience {@link U#Choose(boolean, Supplier)} method to create a new instance of this class.
//      * It's best practice to statically import this function in client code.
//      *
//      * @param <T> the return type
//      */
//     public static class Choice<T> {
//         private final L<V2<Boolean, Supplier<T>>> choices;
//         
//         Choice(boolean predicate, Supplier<T> function) {
//             choices = l(v(predicate, function));
//         }
//         
//         /**
//          * Adds an "or" joined option.
//          */
//         public Choice<T> Or(boolean predicate, Supplier<T> function) {
//             choices.a(v(predicate, function));
//             return this;
//         }
//         
//         /**
//          * Returns the result of the first "or" option which evaluates to <code>true</code> or the default value provided if there is no valid option.
//          */
//         public T or(T defaultValue) {
//             V2<Boolean, Supplier<T>> choice = choices.find(it -> it.get0() == true);
//             return choice != null ? choice.get1().get() : defaultValue;
//         }
//         
//         /**
//          * Returns the result of the first "or" option which evaluates to <code>true</code> or <code>null</code> if there is no valid option.
//          */
//         public T orNull() {
//             return or(null);
//         }
//         
//         /**
//          * Returns the result of the first "or" option which evaluates to <code>true</code> or throws a {@link NoValidChoiceException} if there is no valid option.
//          */
//         public T orThrow() throws NoValidChoiceException {
//             V2<Boolean, Supplier<T>> choice = choices.find(it -> it.get0() == true);
//             if (choice != null) {
//                 return choice.get1().get();
//             }
//             else {
//                 throw new NoValidChoiceException();
//             }
//         }
//         
//         /**
//          * Signals that none of the {@link Choice}s provided resolved to <code>true</code>.
//          */
//         public static class NoValidChoiceException extends Exception {
//             
//         }
//     }
// }
// 
// Path: src/main/java/ch/codebulb/lambdaomega/abstractions/OmegaObject.java
// public abstract class OmegaObject {
//     /**
//      * Prints itself to the standard output.
//      */
//     public void println() {
//         U.println(this);
//     }
// }


// Path: src/main/java/ch/codebulb/lambdaomega/Promise.java
import static ch.codebulb.lambdaomega.L.l;
import static ch.codebulb.lambdaomega.U.*;
import ch.codebulb.lambdaomega.abstractions.OmegaObject;
import java.util.List;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CompletionStage;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executor;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;
import java.util.function.BiConsumer;
import java.util.function.BiFunction;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;

            public CompletionStage<U> apply(T t) {
                return fn.apply(t).wrapped;
            }
        };
    }
    
    /**
     * @see #then(Function, boolean, Executor)
     */
    public <U> Promise<U> then(Function<? super T, ? extends Promise<U>> fn, boolean async) {
        return then(fn, async, null);
    }
    
    /**
     * @see #then(Function, boolean, Executor)
     */
    public <U> Promise<U> then(Function<? super T, ? extends Promise<U>> fn) {
        return then(fn, false);
    }
    
    /**
     * Like {@link CompletableFuture#allOf(CompletableFuture...)}, but includes a bugfix for the problem described 
     * <a href="http://www.codebulb.ch/2015/07/completablefuture-clean-callbacks-with-java-8s-promises-part-4.html#advanced">here</a>:
     * "Unfortunately, the resulting combined promise is of type <code>&lt;{@link Void}&gt;</code>, leading to the ridiculous need to create a 
     * listener which takes a single parameter of type {@link Void}. Typically, we would much rather like to have a resulting 
     * promise working with the collected results of the combined promises, i.e. of Type <code>&lt;List&lt;�&gt;&gt;</code>."
     * This problem is fixed in this implementation.
     */
    public static <T> Promise<List<T>> allOf(Promise<T>... cfs) {
        Promise<Void> allDoneFuture = new Promise<>(
                CompletableFuture.allOf(l(cfs).map(it -> it.wrapped)