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

com.jnape.palatable.lambda.optics.lenses.CollectionLens Maven / Gradle / Ivy

There is a newer version: 5.5.0
Show newest version
package com.jnape.palatable.lambda.optics.lenses;

import com.jnape.palatable.lambda.functions.Fn1;
import com.jnape.palatable.lambda.optics.Lens;

import java.util.Collection;
import java.util.HashSet;
import java.util.Set;
import java.util.stream.Stream;

import static com.jnape.palatable.lambda.optics.Lens.simpleLens;

/**
 * Lenses that operate on {@link Collection}s.
 */
public final class CollectionLens {

    private CollectionLens() {
    }

    /**
     * Convenience static factory method for creating a lens that focuses on a copy of a Collection, given
     * a function that creates the copy. Useful for composition to avoid mutating a Collection reference.
     *
     * @param copyFn the copying function
     * @param     the collection element type
     * @param    the type of the collection
     * @return a lens that focuses on a copy of CX
     */
    public static > Lens.Simple asCopy(Fn1 copyFn) {
        return simpleLens(copyFn, (__, copy) -> copy);
    }

    /**
     * Convenience static factory method for creating a lens that focuses on an arbitrary {@link Collection} as a
     * {@link Set}.
     *
     * @param copyFn the copying function
     * @param     the collection element type
     * @param    the type of the collection
     * @return a lens that focuses on a Collection as a Set
     */
    public static > Lens.Simple> asSet(Fn1 copyFn) {
        return simpleLens(HashSet::new, (xsL, xsS) -> {
            Set missing = new HashSet<>(xsS);
            missing.removeAll(xsL);
            CX updated = copyFn.apply(xsL);
            updated.addAll(missing);
            updated.retainAll(xsS);
            return updated;
        });
    }

    /**
     * Convenience static factory method for creating a lens that focuses on a Collection as a Stream.
     * 

* Note that this lens is effectively lawful, though difficult to prove given the intrinsically * stateful and inequitable nature of {@link Stream}. * * @param copyFn the copying function * @param the collection element type * @param the type of the collection * @return a lens that focuses on a Collection as a stream. */ @SuppressWarnings("RedundantTypeArguments") public static > Lens.Simple> asStream( Fn1 copyFn) { return simpleLens(Collection::stream, (xsL, xsS) -> { CX updated = copyFn.apply(xsL); updated.clear(); xsS.forEach(updated::add); return updated; }); } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy