Interface RelationalExpression

    • Method Detail

      • bindTo

        @Nonnull
        default Stream<PlannerBindings> bindTo​(@Nonnull
                                               ExpressionMatcher<? extends Bindable> matcher)
        Matches a matcher expression to an expression tree rooted at this node, adding to some existing bindings.
        Specified by:
        bindTo in interface Bindable
        Parameters:
        matcher - the matcher to match against
        Returns:
        the existing bindings extended with some new ones if the match was successful or Optional.empty() otherwise
      • getQuantifiers

        @Nonnull
        List<? extends Quantifier> getQuantifiers()
        Return an iterator of references to the children of this planner expression. The iterators returned by different calls are guaranteed to be independent (i.e., advancing one will not advance another). However, they might point to the same object, as when Collections.emptyIterator() is returned. The returned iterator should be treated as an immutable object and may throw an exception if Iterator.remove() is called. The iterator must return its elements in a consistent order.
        Returns:
        an iterator of references to the children of this planner expression
      • canCorrelate

        default boolean canCorrelate()
        Returns if this expression can be the anchor of a correlation. A correlation is always formed between three entities:
        1. the Quantifier that flows data
        2. 2. the anchor (which is a RelationalExpression) that ranges directly over the source
        3. 3. the consumers (or dependents) of the correlation which must be a descendant of the anchor.
        In order for a correlation to be meaningful, the anchor must define how data is bound and used by all dependents. For most expressions it is not meaningful or even possible to define correlation in such a way. For instance, a LogicalUnorderedUnionExpression cannot correlate (this method returns false) because it is not meaningful to bind a record from one child of the union while providing bound values to another. In another example, a logical select expression can correlate which means that one child of the SELECT expression can be evaluated and the resulting records can bound individually one after another. For each bound record flowing along that quantifier the other children of the SELECT expression can be evaluated, potentially causing more correlation values to be bound, etc. These concepts follow closely to the mechanics of what SQL calls a query block. The existence of a correlation between source, anchor, and dependents may adversely affect planning because a correlation always imposes order between the evaluated of children of an expression. This may or may not tie the hands of the planner to produce an optimal plan. In certain cases, queries written in a correlated way can be de-correlated to allow for better optimization techniques.
        Returns:
        true if this expression can be the anchor of a correlation, false otherwise.
      • hashCodeWithoutChildren

        int hashCodeWithoutChildren()
      • semanticEquals

        default boolean semanticEquals​(@Nullable
                                       Object other)
        Overloaded method to call semanticEquals(java.lang.Object) with an empty alias map.
        Parameters:
        other - object to compare to this expression
        Returns:
        true if this object is semantically equal to other that is this and other produce the same result when invoked with no bindings, false otherwise.
      • semanticEquals

        default boolean semanticEquals​(@Nullable
                                       Object other,
                                       @Nonnull
                                       AliasMap equivalenceMap)
        Description copied from interface: Correlated
        Determine equality with respect to an equivalence map between CorrelationIdentifiers based on semantic equality: equality of the plan fragments implementing under the given correlation bindings. The contract of this variant of equals() differs from its regular Java counterpart. A correlation is mostly just one part inside of composition of objects that expresses a more complicated (correlated) structure such as a filter. For instance q1.x = 5 uses a correlation to q1. That entity representing the filter is said to be correlated to q1. Similarly, q1.x = 6 is a different filter and is not equal under any correlation mapping. In contrast, consider a predicate where everything except the correlation is the same, such as q2.x = 5. Without a binding, these two filters are not the same. However, the filters may be a part of some other entity that can express correlations: SELECT * FROM T as q1 WHERE q1.x = 5 is equal to SELECT * FROM T as q2 WHERE q2.x = 5. It does not matter that q1 and q2 are named differently. It is important, however, that their semantic meaning is the same. In the example both q1 and q2 refer to a record type T which presumably is the same record type. Therefore, these two query blocks are the same, even though they are labelled differently. In the context of this method, we can establish equality between q1.x = 5 and q2.x = 5 if we know that q1 and q2 refer to the same underlying entity. The equivalence map passed in encodes that equality between CorrelationIdentifiers. Note: This method has the same interaction with Object.hashCode() as the regular equals() method. As we can only ever establish true equality using equivalence maps, hashCode() implementations in implementors of this interface must not be dependent on any correlation identifiers used in the structure of the entity. Doing so might violate the fundamental property of hash codes: e1.equals(e2, ...) => e1.hashCode() == e2.hashCode()
        Specified by:
        semanticEquals in interface Correlated<RelationalExpression>
        Parameters:
        other - the other object to establish equality with
        equivalenceMap - a map of CorrelationIdentifiers ids to ids'. A correlation identifier id used in this should be considered equal to another correlation identifier id' used in other if either they are the same by Object.equals(java.lang.Object) of if there is a mapping from id to id'.
        Returns:
        true if both entities are considered equal using the equivalences passed in, false otherwise
      • semanticHashCode

        default int semanticHashCode()
        Description copied from interface: Correlated
        Return a semantic hash code for this object. The hash code must obey the convention that for any two objects o1 and o2 and for every AliasMap aliasMap:
         o1.semanticEquals(o1, aliasMap) follows o1.semanticHash() == o2.semanticHash()
         
        If the semantic hash code of two implementing objects is equal and Correlated.semanticEquals(java.lang.Object, com.apple.foundationdb.record.query.plan.temp.AliasMap) returns true for these two objects the plan fragments are considered to produce the same result under the given correlations bindings. The left side o1.semanticEquals(o1, aliasMap) depends on an AliasMap while o1.semanticHash() == o2.semanticHash() does not. Hence, the hash that is computed is identical regardless of possible bindings.
        Specified by:
        semanticHashCode in interface Correlated<RelationalExpression>
        Returns:
        the semantic hash code
      • acceptPropertyVisitor

        @Nullable
        default <U> U acceptPropertyVisitor​(@Nonnull
                                            PlannerProperty<U> visitor)
        Apply the given property visitor to this planner expression and its children. Returns null if PlannerProperty.shouldVisit(RelationalExpression) called on this expression returns false.
        Type Parameters:
        U - the type of the evaluated property
        Parameters:
        visitor - a PlannerProperty visitor to evaluate
        Returns:
        the result of evaluating the property on the subtree rooted at this expression
      • show

        @Nonnull
        default String show​(boolean renderSingleGroups)
        This is needed for graph integration into IntelliJ as IntelliJ only ever evaluates selfish methods. Add this method as a custom renderer for the type RelationalExpression. During debugging you can then for instance click show() on an instance and enjoy the query graph it represents rendered in your standard browser.
        Parameters:
        renderSingleGroups - whether to render group references with just one member
        Returns:
        the String "Done."