Class Triptional<T>

  • Type Parameters:
    T - the type of value in the Triptional

    public class Triptional<T>
    extends java.lang.Object
    A container object which has three possible distinct states:
    • Present with a non-null value
    • Present with a null value
    • Absent
    This three-state object can be understood as an extension or generalization of Optional, which allows one to distinguish between a "present and null" value and an "absent" value.

    Similar to Optional, this is a value-based class; use of identity-sensitive operations (including reference equality (==), identity hash code, or synchronization) on instances of Triptional may have unpredictable results and should be avoided. The motivation for creating this type is as follows:

    In the persistence-layer we manage objects representing DB values, and since the DB supports NULL as a valid field value, this resulted in two types that require a three-state representation of fields:

    1. In Entity which holds fields fetched from the DB, a field can be either:
      • Fetched with a non-null value
      • Fetched with a null value
      • Not fetched
    2. In EntityChange (command) a field can be either:
      • Changed by the command to a non-null value
      • Changed by the command to a null value
      • Not in the command (unchanged)
    • Method Summary

      All Methods Static Methods Instance Methods Concrete Methods 
      Modifier and Type Method Description
      static <T> Triptional<T> absent()
      Returns an absent Triptional instance.
      java.util.Optional<T> asOptional()
      Returns an {code Optional} with the value, if present and not-null; otherwise (whether present with a null value or absent) - return an empty Optional.
      This method is in effect a "reduction" operation where two distinct states of Triptional, null and absent, are mapped to the same empty Optional.
      boolean equals​(java.lang.Object obj)
      Indicates whether some other object is "equal to" this Triptional.
      boolean equals​(java.lang.Object obj, java.util.function.BiFunction<T,​T,​java.lang.Boolean> valueEqualityFunction)
      Indicates whether some other object is "equal to" this Triptional using the input function to test equality.
      The other object is considered equal if: it is also a Triptional and; both instances have no value present or; both instances have a value present (possibly null), and when the valueEqualityFunction is applied to both values it returns true
      boolean equalsValue​(T value)
      Return true if there is a value present (possibly null), and it equals the input; otherwise false
      Triptional<T> filter​(java.util.function.Predicate<? super T> predicate)
      If a value is present, and the value matches the given predicate, returns an Triptional describing the value, otherwise returns an absent Triptional.
      <U> Triptional<U> flatMap​(java.util.function.Function<? super T,​Triptional<U>> mapper)
      If a value is present and not-null, apply the Triptional-bearing notNullMapper() function to it, and return that result.
      If a value is present and null, return a null Triptional .
      Otherwise - return an absent Triptional.
      This method is similar to Optional.flatMap(java.util.function.Function<? super T, ? extends java.util.Optional<? extends U>>) except that it will preserve a present null value as well (will not turn it into an absent Triptional}
      <U> Triptional<U> flatMap​(java.util.function.Function<? super T,​Triptional<U>> notNullMapper, java.util.function.Supplier<Triptional<U>> nullReplacer)
      If a value is present and not-null, apply the Triptional-bearing notNullMapper() function to it, and return that result.
      If a value is present and null, call the nullReplacer() Triptional-bearing function, and return that result.
      Otherwise - return an absent Triptional.
      T get()
      If a value is present in this Triptional (including possibly null), returns the value, otherwise throws NoSuchElementException.
      int hashCode()
      Returns a hash code value which is the combination of: The present value, if any, or 0 (zero) if no value is present. An internal indicator to differentiate between a present and an absent value (without this, a present value of null and an absent value would produce the same hashcode)
      void ifNotNull​(java.util.function.Consumer<? super T> consumer)
      If a value is present and not-null, invoke the specified consumer with the value, otherwise do nothing.
      boolean isAbsent()
      Return true if there is no value present, otherwise false.
      boolean isNotNull()
      Return true if the value is present and not null, otherwise false.
      boolean isNull()
      Return true if the value is present and null, otherwise false.
      boolean isNullOrAbsent()
      Return true if the value is present and null or no value, otherwise false.
      boolean isPresent()
      Return true if there is a value present, otherwise false.
      <U> Triptional<U> map​(java.util.function.Function<? super T,​? extends U> mapper)
      If a value is present and not-null, apply the mapper() function to it, and return a Triptional describing the result.
      If a value is present and null, return a null Triptional instance.
      Otherwise - return an absent Triptional.
      This method is similar to Optional.map(java.util.function.Function<? super T, ? extends U>) except that it will preserve a present null value as well (will not turn it into an absent Triptional}
      <U> Triptional<U> map​(java.util.function.Function<? super T,​? extends U> notNullMapper, java.util.function.Supplier<? extends U> nullReplacer)
      If a value is present and not-null, apply the notNullMapper() function to it, and return a Triptional describing the result.
      If a value is present and null, call the nullReplacer() function, and return a Triptional holding the result.
      Otherwise - return an absent Triptional.
      <U> java.util.Optional<U> mapToOptional​(java.util.function.Function<? super T,​? extends U> mapper)
      If a value is present and not-null, apply the notNullMapper() function to it, and return a Optional holding the result, or an empty Optional if the result is null.
      Otherwise - return an empty Optional.
      <U> java.util.Optional<U> mapToOptional​(java.util.function.Function<? super T,​? extends U> notNullMapper, java.util.function.Supplier<? extends U> nullReplacer)
      If a value is present and not-null, apply the notNullMapper() function to it, and return a Optional holding the result, or an empty Optional if the result is null.
      If a value is present and null, call the nullReplacer() function, and return an Optional holding the result, or an empty Optional if the result is null.
      Otherwise - return an empty Optional.
      boolean matches​(java.util.function.Predicate<? super T> predicate)
      Return true if there is a value is present, and it matches the given predicate; otherwise return false
      static <T> Triptional<T> nullInstance()
      Returns an null Triptional instance - meaning that it is present but with a null value.
      Note Though it may be tempting to do so, avoid testing if an object is null by comparing with == against instances returned by Triptional.nullInstance().
      static <T> Triptional<T> of​(T value)
      Returns a Triptional with the specified present value, can be null.
      java.lang.String toString()
      Returns a non-empty string representation of this Triptional suitable for debugging.
      • Methods inherited from class java.lang.Object

        clone, finalize, getClass, notify, notifyAll, wait, wait, wait
    • Method Detail

      • of

        public static <T> Triptional<T> of​(T value)
        Returns a Triptional with the specified present value, can be null.
        Type Parameters:
        T - the class of the value
        Parameters:
        value - the value to be present, can be null
        Returns:
        a Triptional with the value present
      • nullInstance

        public static <T> Triptional<T> nullInstance()
        Returns an null Triptional instance - meaning that it is present but with a null value.
        Note Though it may be tempting to do so, avoid testing if an object is null by comparing with == against instances returned by Triptional.nullInstance(). There is no guarantee that it is a singleton. Instead, use isNull().
        Type Parameters:
        T - Type of the null value
        Returns:
        a null Triptional
      • absent

        public static <T> Triptional<T> absent()
        Returns an absent Triptional instance. No value is present for this Triptional. Note Though it may be tempting to do so, avoid testing if an object is empty by comparing with == against instances returned by Triptional.absent(). There is no guarantee that it is a singleton. Instead, use either isPresent() or isAbsent().
        Type Parameters:
        T - Type of the absent value
        Returns:
        an absent Triptional
      • get

        public T get()
        If a value is present in this Triptional (including possibly null), returns the value, otherwise throws NoSuchElementException.
        Returns:
        the value held by this Triptional, may be null
        Throws:
        java.util.NoSuchElementException - if there is no value present
        See Also:
        isPresent()
      • ifNotNull

        public void ifNotNull​(java.util.function.Consumer<? super T> consumer)
        If a value is present and not-null, invoke the specified consumer with the value, otherwise do nothing.
        Parameters:
        consumer - block to be executed if a value is present and not-null
      • map

        public <U> Triptional<U> map​(java.util.function.Function<? super T,​? extends U> mapper)
        If a value is present and not-null, apply the mapper() function to it, and return a Triptional describing the result.
        If a value is present and null, return a null Triptional instance.
        Otherwise - return an absent Triptional.
        This method is similar to Optional.map(java.util.function.Function<? super T, ? extends U>) except that it will preserve a present null value as well (will not turn it into an absent Triptional}
        Type Parameters:
        U - The type of the result of the mapping function
        Parameters:
        mapper - a mapping function to apply to the value, if present and not-null
        Returns:
        a Triptional describing the result of applying the mapper, if it is present and not-null; or a null Triptional, if it is present and null; otherwise - an absent Triptional
        Throws:
        java.lang.NullPointerException - if the mapper function is null
      • map

        public <U> Triptional<U> map​(java.util.function.Function<? super T,​? extends U> notNullMapper,
                                     java.util.function.Supplier<? extends U> nullReplacer)
        If a value is present and not-null, apply the notNullMapper() function to it, and return a Triptional describing the result.
        If a value is present and null, call the nullReplacer() function, and return a Triptional holding the result.
        Otherwise - return an absent Triptional. Note This method is similar to Optional.map(java.util.function.Function<? super T, ? extends U>) except that it also allows for a separately-defined replacement operation in case of a present null value. This is convenient in case some default value is required to replace the null.
        For example - the following code will convert numbers into their string representations, unless the number is null, in which case it will be replaced with an empty string:
        
             final Integer number = readNumber();
             final Triptional<String> triptional = Triptional.of(number).map(String::valueOf, () -> "");
         
        Type Parameters:
        U - The type of the result of the mapping function
        Parameters:
        notNullMapper - a mapping function to apply to the value, if present and not-null
        nullReplacer - a function to calculate a replacement value, if present and null
        Returns:
        a Triptional describing the result of applying the notNullMapper function to the value of this Triptional, if it is present and not-null; or a Triptional holding the result of the nullReplacer function, if present and null; otherwise - an absent Triptional
        Throws:
        java.lang.NullPointerException - if the notNullMapper function is null or the nullReplacer function is null
      • flatMap

        public <U> Triptional<U> flatMap​(java.util.function.Function<? super T,​Triptional<U>> mapper)
        If a value is present and not-null, apply the Triptional-bearing notNullMapper() function to it, and return that result.
        If a value is present and null, return a null Triptional .
        Otherwise - return an absent Triptional.
        This method is similar to Optional.flatMap(java.util.function.Function<? super T, ? extends java.util.Optional<? extends U>>) except that it will preserve a present null value as well (will not turn it into an absent Triptional}
        Type Parameters:
        U - The type of the result of the mapping function
        Parameters:
        mapper - a Triptional-bearing mapping function to apply to the value, if present and value not-null
        Returns:
        the result of applying the notNullMapper function, if present and value not-null; or a null Triptional, if present and value is null; otherwise - an absent Triptional
        Throws:
        java.lang.NullPointerException - if the mapper function is null, or if it returns a null result
      • flatMap

        public <U> Triptional<U> flatMap​(java.util.function.Function<? super T,​Triptional<U>> notNullMapper,
                                         java.util.function.Supplier<Triptional<U>> nullReplacer)
        If a value is present and not-null, apply the Triptional-bearing notNullMapper() function to it, and return that result.
        If a value is present and null, call the nullReplacer() Triptional-bearing function, and return that result.
        Otherwise - return an absent Triptional. Note This method is similar to Optional.flatMap(java.util.function.Function<? super T, ? extends java.util.Optional<? extends U>>) except that it also allows for a separately-defined replacement for a null value. This is convenient in case some operation requires a default value to replace the null.
        For example - the following code converts a nested Triptional holding a number into a single one, unless the inner object is a null Triptional, in which case it will be replaced by a zero:
        
             final Triptional<Triptional<Integer>> nested = readNestedTriptional();
             final Triptional<Integer> flattened = nested.flatMap(Function.identity(), () -> 0);
         
        Type Parameters:
        U - The type of the result of the mapping function
        Parameters:
        notNullMapper - a Triptional-bearing mapping function to apply to the value, if present and value not-null
        nullReplacer - a Triptional-bearing function to calculate a replacement instance, if present and value is null
        Returns:
        the result of applying the notNullMapper function, if present and value not-null; or the result of calling the nullReplacer function, if present and value is null; otherwise - an absent Triptional
        Throws:
        java.lang.NullPointerException - if either of the input functions are null, or if either one of them returns a null result
      • asOptional

        public java.util.Optional<T> asOptional()
        Returns an {code Optional} with the value, if present and not-null; otherwise (whether present with a null value or absent) - return an empty Optional.
        This method is in effect a "reduction" operation where two distinct states of Triptional, null and absent, are mapped to the same empty Optional.
        Returns:
        an {code Optional} with a value, if present and not-null, otherwise - an empty Optional
      • mapToOptional

        public <U> java.util.Optional<U> mapToOptional​(java.util.function.Function<? super T,​? extends U> mapper)
        If a value is present and not-null, apply the notNullMapper() function to it, and return a Optional holding the result, or an empty Optional if the result is null.
        Otherwise - return an empty Optional.
        Type Parameters:
        U - The type of the result of the mapping function
        Parameters:
        mapper - a mapping function to apply to the value, if present and not-null
        Returns:
        an Optional holding the result of applying the mapper function to the value of this Triptional, if it is present and not-null; otherwise - an empty Optional
        Throws:
        java.lang.NullPointerException - if the mapper function is null
      • mapToOptional

        public <U> java.util.Optional<U> mapToOptional​(java.util.function.Function<? super T,​? extends U> notNullMapper,
                                                       java.util.function.Supplier<? extends U> nullReplacer)
        If a value is present and not-null, apply the notNullMapper() function to it, and return a Optional holding the result, or an empty Optional if the result is null.
        If a value is present and null, call the nullReplacer() function, and return an Optional holding the result, or an empty Optional if the result is null.
        Otherwise - return an empty Optional.
        Type Parameters:
        U - The type of the result of the mapping function
        Parameters:
        notNullMapper - a mapping function to apply to the value, if present and not-null
        nullReplacer - a function to calculate a replacement value, if present and null
        Returns:
        an Optional holding the result of applying the notNullMapper function to the value of this Triptional, if it is present and not-null; or an Optional holding the result of the nullReplacer function, if present and null; otherwise - an empty Optional
        Throws:
        java.lang.NullPointerException - if the notNullMapper function is null or the nullReplacer function is null
      • filter

        public Triptional<T> filter​(java.util.function.Predicate<? super T> predicate)
        If a value is present, and the value matches the given predicate, returns an Triptional describing the value, otherwise returns an absent Triptional.
        Parameters:
        predicate - the predicate to apply to a value, if present
        Returns:
        an Triptional describing the value of this Triptional, if a value is present and the value matches the given predicate; otherwise an absent Triptional
        Throws:
        java.lang.NullPointerException - if the predicate is null
      • matches

        public boolean matches​(java.util.function.Predicate<? super T> predicate)
        Return true if there is a value is present, and it matches the given predicate; otherwise return false
        Parameters:
        predicate - the predicate to apply to a value, if present
        Returns:
        true if there is a value is present, and it matches the given predicate; otherwise false
        Throws:
        java.lang.NullPointerException - if the predicate is null
      • isPresent

        public boolean isPresent()
        Return true if there is a value present, otherwise false.
        Returns:
        true if there is a value present, otherwise false
      • isAbsent

        public boolean isAbsent()
        Return true if there is no value present, otherwise false.
        Returns:
        true if there is no value present, otherwise false.
      • isNotNull

        public boolean isNotNull()
        Return true if the value is present and not null, otherwise false.
        Returns:
        true if the value is present and not null, otherwise false.
      • isNullOrAbsent

        public boolean isNullOrAbsent()
        Return true if the value is present and null or no value, otherwise false.
        Returns:
        true if the value is present and null or no value, otherwise false.
      • isNull

        public boolean isNull()
        Return true if the value is present and null, otherwise false.
        Returns:
        true if the value is present and null, otherwise false.
      • equalsValue

        public boolean equalsValue​(T value)
        Return true if there is a value present (possibly null), and it equals the input; otherwise false
        Parameters:
        value - a value to compare to this value
        Returns:
        true if there is a value present, and it equals the input; otherwise false
      • equals

        public boolean equals​(java.lang.Object obj)
        Indicates whether some other object is "equal to" this Triptional. The other object is considered equal if:
        • it is also a Triptional and;
        • both instances have no value present or;
        • both instances have a present and null value or;
        • the present values are "equal to" each other via equals().
        Overrides:
        equals in class java.lang.Object
        Parameters:
        obj - an object to be tested for equality
        Returns:
        true if the other object is "equal to" this object otherwise false
      • equals

        public boolean equals​(java.lang.Object obj,
                              java.util.function.BiFunction<T,​T,​java.lang.Boolean> valueEqualityFunction)
        Indicates whether some other object is "equal to" this Triptional using the input function to test equality.
        The other object is considered equal if:
        • it is also a Triptional and;
        • both instances have no value present or;
        • both instances have a value present (possibly null), and when the valueEqualityFunction is applied to both values it returns true
        Parameters:
        obj - an object to be tested for equality
        valueEqualityFunction - the function to use for testing equality of values, when present
        Returns:
        true if the other object is "equal to" this object otherwise false
        Throws:
        java.lang.NullPointerException - if valueEqualityFunction is null
      • hashCode

        public int hashCode()
        Returns a hash code value which is the combination of:
        • The present value, if any, or 0 (zero) if no value is present.
        • An internal indicator to differentiate between a present and an absent value (without this, a present value of null and an absent value would produce the same hashcode)
        Overrides:
        hashCode in class java.lang.Object
        Returns:
        hash code value of this instance
      • toString

        public java.lang.String toString()
        Returns a non-empty string representation of this Triptional suitable for debugging. The exact presentation format is unspecified and may vary between implementations and versions.
        Implementation Note: If a value is present the result must include its string representation in the result. Absent, null and not-null Triptionals must all be unambiguously differentiable.
        Overrides:
        toString in class java.lang.Object
        Returns:
        the string representation of this instance