Add a Dotexpression like reference to language and combine it with BinaryOperations

Hey,

Sorry for spaming this forum, but I don't know any other way to comprehend the complexity of MPS.

I reused the BinaryOperation expression of baselanguage in my own language and there are also references which look like DotExpressions. Perhaps I could reuse DotExpression as well, but I think I haven't understand what necessary therefore and I guess it's quite a bit overhead.
Unfortunately my DotExpression does not behave like the build in. If I type
a.b > c a tree like in 1) is constructed but it should look like 2) (x is the parent).

    1)2)
    a x
     \              / \
      b            a  c
       \            \
        c            b


I don't know how give my reference expression a priority so that the editors actions behave similar to a baselanguage DotExpression. Perhaps it's the easiest way to implement the DotExpression, but then I need a hint where to begin.

Many thanks!
9 comments
If you extend BinaryOperation, you need to declare the concept property (not property, but concept property) called "priority".
Then internally BinaryOperation will automatically rotate the tree whenever there is a priority violation.
0
Thank you for your reply!
I've seen this priority property, but I don't extend BinaryExpression. I added an expression similar to DotExpression, which also doesn't extend BinaryExpression, to my language. So nodes of my expression can be operands of BinaryExpressions.
0
If your Expression does not extend BinaryExpression, then it would be a bit difficult. All the rotating logic is implemented in ParenthesisUtil. The method you can take a look at is checkOperationWRTPriority inside that class. You will see a bunch of node<BinaryOperation> in there, so it's quite specific to BinaryOperation.

If you don't extend BinaryOperation then you would have to code your own rotation logic.

Also, DotExpression really shouldn't have its right hand side being an Expression.
0
It is not possible to extend my Expression from BinaryExpression, since there is a common super concept for qualified references and simple ones in my language.
I've looked at ParenthesisUtil, which is a bit complex. But as far as I see this class does not care for DotExpression. Where is the code which makes shure that
a.b + c
is build like
(a.b) + c and not like a.(b + c)
0
I don't understand why the situation described above is different from what we have in BaseLanguage. If I simply type a.b > c:
CodeSnipet.png

resulting AS tree will looks like:

AST.png


as you can see, ">" node is on top of the tree having c on the right side and a.b (DotExpression) on the left side, so you can reuse this functionality in your language.

">" node is instance of GraterThanExpression (sub-concept of BinaryOperation). Then you type ">" existing DotExpression (a.b) will be right-transformed into a GraterThanExpression and attached there as left side. This right-transform logic is described by binaryOperations side-transform root in base language.actions model:

              
right transformed node: Expression tag: default_  //transform expression into left operand of binary operation          
  condition :  
    <none>     

  common initializer :        
    <no common variables>     
    ....................................     
    <no common initializer>   

  actions :    
    add concept BinaryOperation              
      handler  
        (operationContext, sourceNode, pattern, model, result)->node<BinaryOperation> { 
  sourceNode.replace with(result); 
  result.leftExpression.set(sourceNode); 
  ParenthesisUtil.checkOperationWRTPriority(result); 
  return result; 
}
prettyPrint();

Please let me know if i did not answered original question.
0
Hello Alex,

Thank you very much for your detailed answer!
But unfortunately I still don't understand, why a.b + c
transforms to (a.b) + c. The operation b of the dot expression is also an expression and it's at the leftmost position to the cursor. So I would expect, that the sourceNode in the right transform action will be the b expression and not the whole dot expression a.b. And since DotExpressions are not handled in checkOperationWRTPriority I really don't understand why it works different with my qualified reference expression compared to the DotExpression.
0
The operation b of the dot expression is also an expression ...

Well, in MPS BaseLanguage operation b is instance of IOperation and not instance of Expression. This can be the reason. DotExpression (parent of "b") is instance of expression, so it can be properly right-transformed...
0
Great, the hint with the IOperation solved my problem. I've found this tranform action:

       
right transformed node: IOperation tag: default_  //same actions as for containing dot-expression
  condition :         
    <none>            
       
  common initializer :
    <no common variables>            
    ....................................            
    <no common initializer>          
       
  actions :           
    include transform menu for       
      (operationContext, sourceNode, model)->node<> { 
  sourceNode.parent; 
}  
prettyPrint();
It is responsible for the DotExpression behavior. I have written a similar action for my expression.
0
yep, you right - original right-transform posted by me doesn't make sense here. ;)
0

Please sign in to leave a comment.