Skip to Content

With Release 7.40 ABAP supports so called constructor operators. Constructor operators are used in constructor expressions to create a result that can be used at operand positions. The syntax for constructor expressions is

… operator type( … ) …

operator is a constructor operator. type is either the explicit name of a data type or the character #. With # the data type can be dreived from the operand position if the operand type is statically known. Inside the parentheses specific parameters can be specified.

Conditional operators COND and SWITCH

Last but not least, two nice ones, the conditionals COND and SWITCH.

  • … COND dtype|#( WHEN log_exp1 THEN result1
                    [ WHEN log_exp2 THEN result2 ]
                    …
                    [ ELSE resultn ] ) …

       constructs a result of the specified type that depends on logical expressions.

  • … SWITCH dtype|#( operand
                        WHEN const1 THEN result1
                      [ WHEN const2 THEN result2 ]
                      …
                      [ ELSE resultn ] ) …

constructs a result of the specified type that depends on a case differentiation.

With other words: IF and CASE as expressions in operand positions!

         

Example for COND

DATA(time) =

  COND string(

    WHEN sy-timlo < ‘120000’ THEN

      |{ sy-timlo TIME = ISO } AM|

    WHEN sy-timlo > ‘120000’ THEN

      |{ CONV t( sy-timlo – 12 * 3600 )

         TIME = ISO } PM|

    WHEN sy-timlo = ‘120000’ THEN

      |High Noon|

    ELSE

      THROW cx_cant_be( ) ).

Note the THROW. Now you can raise and  throw exceptions …

Example for SWITCH

CLASS cx_langu_not_supported DEFINITION INHERITING FROM cx_static_check.
ENDCLASS.

CLASS class DEFINITION.
  PUBLIC SECTION.
    METHODS meth IMPORTING iso_langu   TYPE string
                 RETURNING VALUE(text) TYPE string.
ENDCLASS.

CLASS class IMPLEMENTATION.
  METHOD meth.
    …
  ENDMETHOD.
ENDCLASS.

  DATA(text) =
    NEW class(
      )->meth(
          SWITCH #( sy-langu
                    WHEN ‘D’ THEN `DE`
                    WHEN ‘E’ THEN `EN`
                    ELSE THROW cx_langu_not_supported( ) ) ).

Amazing, n’est-ce pas?

To report this post you need to login first.

12 Comments

You must be Logged on to comment or reply to a post.

    1. Horst Keller
      Post author

      The exception is not thrown inside meth but in the context where meth is called. This context must have a raising clause which is not shown here.

      (0) 
  1. Paul Hardy

    While we are talking about local classes and methods, are there any plans in 740 or beyond, that when you re writing your code and call a method of a class and it does not exists, you get the “method does not exists – do you want to create it?” and it creates a skeleton implementation and defintion, which is the case for PERFORM routines.

    This would speed up test driven development enormously. Sometimes people wonder why programmers are slow to adopt OO, it is little niggly things like this that make writing methods more work than form routines. People are lazy so they take the easy option.

    I was told this is possible in ABAP in Eclipse…..

    (0) 
    1. Horst Keller
      Post author

      No support for this in SAP GUI but in (at least my) Eclipse, crtl+F1 on class=>meth( ) and it will create the method for you.

      Nevertheless, from my learning of ABAP long time ago I remember some very misleading effects from this. In old ABAP trainings they’ve explained subroutines (FORMs) coming from PERFORM. First write PERFORM. double click, implement. Problem was that people did not understand that the FORM and its parameter interface are the important part and that PERFORM is only its user. There were big problems in explaining the modes forparameter  passing because everything was based on PERFORM and not on FORM where the real definition lies. But let’s expect, that nowadays developers know what they are doing …

      (0) 
  2. Former Member

    The COND has been very useful as a sort of ternary operator to streamline code that would otherwise look very convoluted.

    Sadly, it seems that the editor’s syntax highlighting has not been updated for this notation and it will mark parts of the statement in red, indicating they are invalid even though it compiles and executes fine. Are there plans to update the syntax highlighter to support these statements? (Tested in 7.4 SP7 and SP9)

    (0) 
  3. Jacques Nomssi

    Hello Horst,

    I am not able to specify an object reference type as a result to COND/SWITCH directly. I can write:

    METHODS output IMPORTING iv_ucomm       TYPE syucomm
                   RETURNING VALUE(rv_flag) TYPE flag.
    METHOD output.
      DATA li_export TYPE REF TO lif_output.
    
      li_export = SWITCH #( iv_ucomm WHEN 'FC01' THEN NEW lcl_plantuml_output( )
                                     WHEN 'ONLI' THEN NEW lcl_xmi_output( )
                                     ELSE NEW lcl_null_output( ) ).
      rv_flag = li_export->output( NEW lcl_parameter( ) ).
    ENDMETHOD.

    where LIF_OUTPUT is an interface implemented by the 3 classes, but what I really want is to write

      rv_flag = SWITCH lif_output( iv_ucomm 
        WHEN 'FC01' THEN NEW lcl_plantuml_output( )
        WHEN 'ONLI' THEN NEW lcl_xmi_output( )
        ELSE NEW lcl_null_output( )   )->output( NEW lcl_parameter( ) ).  

    but this triggers the error “object type LIF_OUTPUT can only be referenced using “REF TO”. However, the following is valid (but I have to cast twice for type inference):

    rv_flag = CAST lif_output( SWITCH #( iv_ucomm
          WHEN 'FC01' THEN CAST lif_output( NEW lcl_plantuml_output( ) )
          WHEN 'ONLI' THEN NEW lcl_xmi_output( )
          ELSE NEW lcl_null_output( ) ) )->output( NEW lcl_parameter( ) ).

    Can this be improved? (I am testing on 7.50 SP02). Did I missed some documentation?

    best regards,

    JNN

     

    (1) 
    1. Horst Keller
      Post author

      Hello Jacques,

      What you are trying to do is a chaining with constructor operator SWITCH:

      … = SWITCH ref_type( … )->meth( ).

      This is not allowed and not documented. Only “Expressions with the operators NEW and CAST can be positioned directly before the object component selector -> and can occur in chainings.”

      As far as I know, there are no immediate plans for allowing chainnings for arbitrary constructor operators.

      Kind regards

      Horst

      PS:

      SWITCH #( WHEN ref1 IS BOUND THEN ref1->meth( ) ELSE ref2->meth( ) )

      is preferable to

      SWITCH reftype( WHEN ref1 IS BOUND THEN ref1 ELSE ref2 )->meth( )

      because of obfuscation.

       

      (1) 

Leave a Reply