All Downloads are FREE. Search and download functionalities are using the official Maven repository.

me.shaftesbury.utils.functional.UnaryFunction Maven / Gradle / Ivy

There is a newer version: 1.17
Show newest version
package me.shaftesbury.utils.functional;

/**
 * An implementation of {@link me.shaftesbury.utils.functional.Func} that is intended for use by the {@link me.shaftesbury.utils.functional.MException}
 * @param  the type of the argument of the function
 * @param  the type of the return value of the function
 */
public abstract class UnaryFunction implements Func
{
    /**
     * Functional composition. Return a new function which, when evaluated, returns the composition of the current {@link me.shaftesbury.utils.functional.UnaryFunction}
     * and the supplied {@link me.shaftesbury.utils.functional.Func} parameter.
     * @param f the single-argument function to be composed with this
     * @param  the type of the return value of f
     * @return a {@link me.shaftesbury.utils.functional.UnaryFunction} that accepts a parameter of type A and returns a datum of type C
     * @see Function Composition
     */
    public UnaryFunction then(final Func f)
    {
        return compose(this,f);
    }

    private static final UnaryFunction compose(final Func f, final Func g)
    {
        return new UnaryFunction()
        {
            public C apply(final A a) { return g.apply(f.apply(a));}
        };
    }

    /**
     * Given a {@link me.shaftesbury.utils.functional.Func} and its argument, produce a function of no arguments that
     * can be evaluated at a later point.
     * @param f the one-parameter function
     * @param a the parameter of f
     * @param  the type of the parameter of f
     * @param  the type of the return value of the delayed function
     * @return a function that takes no arguments and returns a value of type B
     */
    public static final Func0 delay(final Func f, final A a)
    {
        return new Func0()
        {
            @Override
            public B apply() {
                return f.apply(a);
            }
        };
    }
}