Hello friends,
I have been learning about the top-down optimizer and I am trying to
understand the semantics of the passThrough and derive calls. I have a few
questions about those.
1. The main passThrough call is `RelNode passThrough(RelTraitSet
required)`. It is my understanding that this is called when the optimizer
wants to "rewrite" a `RelNode` to have certain `required` traits. Few
questions here:
1. This "rewrite" may involve passing the traits down to the
children. All the example implementations that I have come across only
propagate the traits down one depth from parent to children.
That is, there
is no recursive `passThrough` call on the children. Is that recursive
propagation handled in the `TopDownRuleDriver` somewhere?
2. What should the behavior of a RelNode be when it is unable to
honor the requirements? Should it return null?
3. At what point does the enforcer operator come into play? Is it
the RelNodes responsibility to add the enforcer operator for
cases where it
is unable to honor a traitset or does the planner somehow do that
automatically?
4. The current `RelNode` may already have certain traits. Should the
required traits overwrite the existing traits or should they be "merged"
into the existing traits?
2. I am unclear on the semantics of the `derive` call. The various
derive modes add to my confusion.
1. I tried searching for DeriveMode.BOTH and found no references in
the main planner machinery for it. Is the implementation of that
currently
incomplete? Only LEFT_FIRST, RIGHT_FIRST and OMAKASE are referenced in
TopDownRuleDriver.java.
2. Can someone briefly explain what are the expected semantics of the
following calls? I am confused by the semantics because the first one
returns a single RelNode vs the second one returns a List<> and the
arguments are also quite different between the two methods.
1. RelNode derive(RelTraitSet childTraits, int childId);
2. List<RelNode> derive(List<List<RelTraitSet>> inputTraits);
3. Looking at the default implementation of RelNode
derive(RelTraitSet childTraits, int childId) confused me a bit. My
understanding of derive was that it will take the child's traits and pass
those up the tree. But the default implementation is also
calling `convert`
on the children. That suggests that even the children are being
modified in
this call. Why is that necessary?
Apologies for the barrage of questions and thanks in advance for in advance.
Regards!