I'm a little unclear why this making UnaryOperatorNode extend
ParameterNode and the subsequent changes are needed. Currently
triggers/views can check to see if the statement has a parameter node
anywhere in the tree without having every node implement ParameterNode,
so what is different about UnaryOperatorNode now?


I agree with Dan that it's not a good idea to make UnaryOperatorNode extend ParameterNode, but I disagree about what we should do about it.

Here's some context --- when it comes to figuring out the type of a node, in almost all cases the type is determined by the node itself, or the node figures it out based on its children. For example, all comparison operators have a type of boolean, while an arithmetic operator node (like +) figures out its type based on its operands (e.g. adding two ints gives an int).

ParameterNode is an exception. It gets its type from the context in which it is used. For example, in:

        t1.int_col = ?

the type of the ? is derived from what it is being compared to.

From a coding point of view, most type resolution is done bottom-up. Each node resolves its children, then figures out what its own type is. Parameters are different in that the type resolution must be done top-down. In the "=" operator in the above example, the children of the equals node are bound first, after which it checks to see whether either child is a parameter node. If so, it takes the type from the non-parameter side and sets the parameter to the same type.

There are something like 13 different cases in which a parameter node can be used, and each case requires some special code of the type I just described. Mamta is trying to avoid introducing even more special-case code. One way to do this is to make UnaryOperatorNode extend ParameterNode.

The biggest problem I have with this is that a unary operator isn't a type of parameter. I think that changing the class hierarchy in this way will only confuse people in the future.

Another problem is that allowing "- ?" is only one possible extension to the cases parameters are allowed. If we add more extensions, will we have to make more node types into parameters? We could eventually end up with a large proportion of ValueNodes as extensions of ParameterNode.

It seems to me that, to determine whether a node needs this special top-down type processing, the code shouldn't be asking whether it's a parameter node. It should ask whether the node (or expression) has to derive its type from context. For example, BinaryOperatorNode could be changed to something like this:

      if (leftOperand.getsTypeFromContext())
      {
          if (rightOperand.getsTypeFromContext())
          {
              throw StandardException.newException(. . .);
          }

          leftOperand.setDescriptor(rightOperand.getTypeServices());
      }

      if (rightOperand.getsTypeFromContext())
      {
          rightOperand.setDescriptor(leftOperand.getTypeServices());
      }

In ValueNode, getsTypeFromContext() would return false. In ParameterNode it would return true. In UnaryArithmeticOperatorNode it would return true if its operand is a ParameterNode and false otherwise (one way to do this is to make it return operand.getsTypeFromContext()).

As for why there are two methods for setting types (setType() and setDescriptor()), they do different things for ParameterNode. All that setType() does is set the type for the node itself. ParameterNode.setDescriptor() also sets the type in the array of parameter types in the StatementNode. There's also some stuff in there having to do with replication/synchronization that could be obsolete (depending on whether this feature is ever resurrected). I agree that it's confusing to have two different methods do similar things. Perhaps the two methods could be collapsed into one.


                       -        Jeff Lichtman
                                [EMAIL PROTECTED]
                                Check out Swazoo Koolak's Web Jukebox at
http://swazoo.com/

Reply via email to