/** * First-class bifunctor map. * * @return A first-class bifunctor map. */ public <B, J> F<F<I, J>, F<F<A, B>, Result<J, B>>> bimap() { return curry(this::bimap); }
/** * Maps the given function across this hash as a contra-variant functor. * * @param g The function to map. * @return A new hash. */ public <B> Hash<B> contramap(final F<B, A> g) { return hash(compose(f, g)); }
/** * Returns a function that moves a value along the enumerator a given number of times. * * @param l The number of times to move along the enumerator. * @return A function that moves a value along the enumerator a given number of times. */ public F<A, Option<A>> plus(final long l) { return flip(plus).f(l); }
/** * Binds the given function <em>f</em> to the values of the given functions, with a final join. * * @param ca A function to bind <em>f</em> function to. * @param cb A function to bind <em>f</em> function to. * @param f The bound function to be composed with <em>ca</em> and then applied with <em>cb</em> * @return A new function after performing the composition, then application. */ public static <A, B, C, D> F<D, C> bind(final F<D, A> ca, final F<D, B> cb, final F<A, F<B, C>> f) { return apply(compose(f, ca), cb); }
/** * Joins two arguments of a function of arity-2 into one argument, yielding a function of arity-1. * * @param f A function whose arguments to join. * @return A function of arity-1 whose argument is substituted for both parameters of <em>f</em>. */ public static <A, B> F<B, A> join(final F<B, F<B, A>> f) { return bind(f, Function.identity()); }
/** * Promotes a function of arity-2 to a higher-order function. * * @param f The function to promote. * @return A function of arity-2 promoted to compose with two functions. */ public static <A, B, C, D> F<F<D, A>, F<F<D, B>, F<D, C>>> lift(final F<A, F<B, C>> f) { return curry((ca, cb) -> bind(ca, cb, f)); }
/** * Turn a stream of functions into a function returning a stream. * * @param fs The stream of functions to sequence into a single function that returns a stream. * @return A function that, when given an argument, applies all the functions in the given stream to it * and returns a stream of the results. */ public static <A, B> F<B, Stream<A>> sequence_(final Stream<F<B, A>> fs) { return fs.foldRight((baf, p1) -> Function.bind(baf, p1._1(), curry((a, stream) -> cons(a, p(stream)))), Function .constant(Stream.nil())); }
/** * Performs a right-fold reduction across this zipper. * * @param f The function to apply on each element of this zipper. * @param z The beginning value to start the application from. * @return the final result after the right-fold reduction. */ public <B> B foldRight(final F<A, F<B, B>> f, final B z) { return left.foldLeft(flip(f), right.cons(focus).foldRight(compose( Function.<P1<B>, B, B>andThen().f(P1.__1()), f), z)); }
/** * The catamorphism for Iterables, implemented as a right fold. * * @param f The function with which to fold the wrapped iterable. * @param z The base case value of the destination type, applied last (rightmost) to the fold. * @return The result of the catamorphism. */ public <B> B foldRight(final F2<A, B, B> f, final B z) { final F<B, B> id = identity(); return foldLeft(curry((k, a, b) -> k.f(f.f(a, b))), id).f(z); }
/** * Applies a given function over the arguments of another function of arity-2. * * @param a The function whose arguments to apply another function over. * @param f The function to apply over the arguments of another function. * @return A function whose arguments are fed through function f, before being passed to function a. */ public static <A, B, C> F<B, F<B, C>> on(final F<A, F<A, C>> a, final F<B, A> f) { return compose(compose(Function.<B, A, C>andThen().f(f), a), f); }
/** * Performs function application within a higher-order function (applicative functor pattern). * * @param cab The higher-order function to apply a function to. * @param ca A function to apply within a higher-order function. * @return A new function after applying the given higher-order function to the given function. */ public static <A, B, C> F<C, B> apply(final F<C, F<A, B>> cab, final F<C, A> ca) { return apply(uncurryF2(cab), ca); }
/** * Function composition flipped. * * @return A function that composes two functions to produce a new function. */ public static <A, B, C> F<F<A, B>, F<F<B, C>, F<A, C>>> andThen() { return g -> f -> andThen(g, f); }
/** * Returns a new list of all the items in this list that do not appear in the given list. * * @param eq an equality for the items of the lists. * @param xs a list to subtract from this list. * @return a list of all the items in this list that do not appear in the given list. */ public final List<A> minus(final Equal<A> eq, final List<A> xs) { return removeAll(compose(Monoid.disjunctionMonoid.sumLeft(), xs.mapM(curry(eq.eq())))); }
/** * Maps the given function across the values of this TreeMap. * * @param f A function to apply to the values of this TreeMap. * @return A new TreeMap with the values transformed by the given function. */ @SuppressWarnings("unchecked") public <W> TreeMap<K, W> map(final F<V, W> f) { final F<P2<K, Option<V>>, P2<K, Option<W>>> g = compose(p2 -> p(p2._1(), p2._2()), P2.map2_(F1Functions.mapOption(f))); final F<K, P2<K, Option<V>>> coord = flip(P.<K, Option<V>>p2()).f(Option.none()); final Ord<K> o = tree.ord().contramap(coord); return new TreeMap<>(tree.map(TreeMap.ord(o), g)); }
/** * Returns the first value found in the list of visitors after application of the given value, otherwise returns the * given default. * * @param visitors The list of visitors to apply. * @param def The default if none of the visitors yield a value. * @param value The value to apply to the visitors. * @return The first value found in the list of visitors after application of the given value, otherwise returns the * given default. */ public static <A, B> B visitor(final List<F<A, Option<B>>> visitors, final F0<B> def, final A value) { return findFirst(visitors.map(Function.apply(value)), def); }