Skip to Content

Do you use changing and exporting parameters in your ABAP methods? I did it a long time. But I’m cured. It all began, when I startet to consider functional programming style (see this excellent blog ). It lead me to avoid changing variable values after having set them once.

Changing: A simple example

class lcl_app implementation.
  method main.
    data ls_line type gty_s_line_to_change.

    ls_line-field1 = p_field1.
    ls_line-field2 = `Value 2`.
    ls_line-field3 = `Value 3`.

    try.
      change_field2( changing cs_line = ls_line ).
      cl_demo_output=>display( ls_line ).
    catch lcx_excpt.
      cl_demo_output=>display( ls_line ).
    endtry.
  endmethod.

  method change_field2.
    cs_line-field2 = `Value 2 changed`.
    if cs_line-field1 = `Oh no!`.
      raise exception type lcx_excpt.
    endif.
  endmethod.
endclass.

In the above code, a changing parameter is used in method change_field2. This method changes one of the fields in the structure passed by changing.

What happens when an exception occurs? Since the change of FIELD2 is done before the RAISE, the field has changed even if the method was interrupted by the exception. If I run this program and put “Oh no!” in the parameter on the selection screen, I get this output:

A better way to achieve this could be:

    methods:
      change_field2
        importing is_line type gty_s_line_to_change
        returning value(rv_res) type string
        raising lcx_excpt.
(...)
class lcl_app implementation.
  method main.
    data ls_line type gty_s_line_to_change.

    ls_line-field1 = p_field1.
    ls_line-field2 = `Value 2`.
    ls_line-field3 = `Value 3`.

    try.
      data(ls_line_changed) = value #(
        base ls_line
        field2 = change_field2( ls_line ) ).
      cl_demo_output=>display( ls_line_changed ).
    catch lcx_excpt.
      cl_demo_output=>display( ls_line_changed ).
    endtry.
  endmethod.

  method change_field2.
    rv_res = `Value 2 changed`.
    if is_line-field1 = `Oh no!`.
      raise exception type lcx_excpt.
    endif.
  endmethod.
endclass.

In this case, you get:

Another issue with changing parameters is that they do not allow using “data(var)” declarations.

Exporting parameters

Well, I really like the functional form of methods which allows to make chainings:

zcl_queue_processor=>process( zcl_queue_provider=>get( ) ).

So, if it comes to several exporting parameters, I tend to create a structure containing all the values I want to get from my method so I can create the method using a return parameter.

Another annoying thing is that exporting parameters that are passed by reference behave exactly as changing parameters. They keep the value of the passed variable if they are not changed in the called method. This is why the extended syntax check throws a warning when you do not initialize them at the beginning of the method.

Performance issues

Since ABAP knows how to “lazy copy”, i.e. to keep a reference  on a copied value until the copied one changes, the disadvantage on performance using the value-based RETURNING par are not too huge. However, when it comes to large tables that are to be changed afterwards, I fall back to a reference EXPORTING var.

Conclusion

All this made me set up a personal programming style rule:

“Whenever possible, use only importing and returning parameters in methods”

What do you think about it?

To report this post you need to login first.

12 Comments

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

  1. Manuel Hofmann

    One could argue does it make sense to use the parameters if an exception is raised? In the end, the method was not able to fulfill its purpose (you raised an exception). So does it make sense to process the parameters? In my opinion no.

    I try too to avoid changing parameter as much a possible, however in the case of exporting i always try to clear them before anything happens.

     

    (2) 
    1. Jörg Krause Post author

      However, the value has changed after the exception has been raised. Maybe it is used further on in a different context. With changing / exporting, you have to care about these things, with returning not.

      (0) 
  2. Jacques Nomssi

     

    As Horst Keller once pointed out,

    changing parameters passed by reference are changed immediately, changing parameters passed by value are only returned if the method is left regularly (without exception) via RETURN or ENDMETHOD.

    you can pass a CHANGING parameter by value.

    JNN

    (1) 
    1. Jörg Krause Post author

      Yes, you are right. As long as I do not forget ticking the “value” checkbox in a changing parameter, I’m save. On the other hand, with returning, I can’t forget it, it’s mandatory.

      (0) 
        1. Jörg Krause Post author

          If you read the blog you mentioned, you will find there that the performance loss you have using returning parameters is about 1/2 percent. The blogger measured the following:

          As you see, the duration of passing a huge data table with returning is almost the same as with exporting. In fact, it was this blog that made me give up the exporting parameters and fancy the returning.

          (0) 
          1. Suhas Saha

            The duration of passing a huge data table with returning is almost the same as with exporting.

            I have read the blog but i would take it with a pinch of salt. I would expect the performance to depend on the width of the table-line. The table in example USR02(44 fields in my system) is narrower than say BSEG(393).

            If you see my blog comment, i am all in with using internal tables as RETURNING but i would pay a special eye on the performance.

            (2) 
  3. Jelena Perfiljeva

    What ABAP methods? LOL 🙂

    It should be just USING and CHANGING, in/out, whatever you call it. The rest is blasphemy. Too many choices, too many problems. Keep it simple, that’s what I think.

     

    (0) 
  4. Michael Biber

    Another option:

    We stated in our development guides that larger pieces of data must be returned using a real reference (REF TO).

    On the other hand this approach has a downside: When does ABAP learn that the result of a method can be dereferenced directly?

    lt_table[] = lr_object->my_method( )->*[].
    (0) 
    1. Jörg Krause Post author

      To me, this approach goes exactly in the opposite direction. Working with data references means,  that if you change your data in method A it will change also in method B without being able to understand where the change came from if not searching in all methods where the reference has been used.

      (0) 
      1. Michael Biber

        I am not sure if I expressed myself correctly. I am not speaking of passing references into a method and change them. I am just talking about the RETURNING parameters. Every caller can be sure to get a fresh data instance when receiving data from a method by a RETURNING parameter.

        (0) 

Leave a Reply