Application Development Blog Posts
Learn and share on deeper, cross technology development topics such as integration and connectivity, automation, cloud extensibility, developing at scale, and security.
cancel
Showing results for 
Search instead for 
Did you mean: 
horst_keller
Product and Topic Expert
Product and Topic Expert
SAP NetWeaver AS for ABAP 7.52 is available now.

It is mainly a "major step on the way to efficient development of SAP HANA optimized SAP Fiori apps is the use of the new RESTful ABAP programming model which includes technologies such as CDS, Business Object Processing Framework (BOPF), SAP Gateway and SAPUI5."

But there are some news in the ABAP language too.

One of those is virtual sorting of internal tables.

Virtual Sorting of Internal Tables


There is a new method VIRTUAL_SORT of class CL_ABAP_ITAB_UTILITIES. With that method, you can virtually sort a set of internal tables. The internal tables of such a set must contain the same number of lines. The method VIRTUAL_SORT treats the set of internal tables as one combined table containing all the columns of the involved internal tables. It sorts that virtual combined table ascending or descending by the columns whose names are passed to the method and returns an array of line numbers of the virtually sorted combined table. This allows you to sort internal tables without changing the order of lines of the internal tables itself, e.g. to generate various sorted output data without affecting the original data.

Step by Step


Let me show it to you in a step by step example.

First, we create some example data in three internal tables.
TYPES:
BEGIN OF flight,
carrid TYPE s_carr_id,
connid TYPE s_conn_id,
cityfrom TYPE s_city,
cityto TYPE s_city,
END OF flight,
flights TYPE STANDARD TABLE OF flight
WITH EMPTY KEY,
BEGIN OF city,
city TYPE s_city,
latitude TYPE s_lati,
longitude TYPE s_long,
END OF city,
cities TYPE STANDARD TABLE OF city
WITH EMPTY KEY.
DATA:
flight_tab TYPE flights,
from_city_tab TYPE cities,
to_city_tab TYPE cities.


SELECT carrid, connid, cityfrom, cityto
FROM spfli
INTO CORRESPONDING FIELDS OF TABLE @flight_tab.

SELECT city, latitude, longitude
FROM sgeocity
INTO TABLE @DATA(cities).

TRY.
from_city_tab = VALUE #( FOR <fs> IN flight_tab
( cities[ city = <fs>-cityfrom ] ) ).
to_city_tab = VALUE #( FOR <fs> IN flight_tab
( cities[ city = <fs>-cityto ] ) ).
CATCH cx_sy_itab_line_not_found.
MESSAGE 'Flight model data not consistent,' &&
' use program SAPBC_DATA_GENERATOR' &&
' to create the data.' TYPE 'X'.
ENDTRY.

There is an internal table flight_tab containing flight data. Two additional tables from_city_tab and to_city_tab are constructed with lines containing the longitudes and latitudes of the departure and arrival cities from the respective lines of flight_tab.

Let's sort the flight data virtually by the longitudes and latitudes of the departure and arrival cities, ascending and descending:
DATA(sort_asc) = cl_abap_itab_utilities=>virtual_sort(
im_virtual_source =
VALUE #(
( source = REF #( from_city_tab )
components =
VALUE #( ( name = 'latitude' )
( name = 'longitude' ) ) )
( source = REF #( to_city_tab )
components =
VALUE #( ( name = 'latitude' )
( name = 'longitude' ) ) )
( source = REF #( flight_tab )
components =
VALUE #( ( name = 'carrid' )
( name = 'connid' ) ) ) ) ).

cl_demo_output=>display( sort_asc ).

DATA(sort_desc) = cl_abap_itab_utilities=>virtual_sort(
im_virtual_source =
VALUE #(
( source = REF #( from_city_tab )
components =
VALUE #( ( name = 'latitude'
descending = abap_true )
( name = 'longitude'
descending = abap_true ) ) )
( source = REF #( to_city_tab )
components =
VALUE #( ( name = 'latitude'
descending = abap_true )
( name = 'longitude'
descending = abap_true ) ) )
( source = REF #( flight_tab )
components =
VALUE #( ( name = 'carrid' )
( name = 'connid' ) ) ) ) ).
cl_demo_output=>display( sort_desc ).

The virtual sorting involves all three internal tables.We simply pass references to the internal tables, the names of the columns used for sorting, and the sort order to method cl_abap_itab_utilities=>virtual_sort. The results are arrays of the line numbers resulting from the ascending and descending sortings.





Normally, you do not want to look at these values, but use them for constructing an output:
DATA sorted_tab TYPE flights.

LOOP AT sort_asc ASSIGNING FIELD-SYMBOL(<idx>).
APPEND flight_tab[ <idx> ] TO sorted_tab.
ENDLOOP.

cl_demo_output=>display( sorted_tab ).

CLEAR sorted_tab.
LOOP AT sort_desc ASSIGNING <idx>.
APPEND flight_tab[ <idx> ] TO sorted_tab.
ENDLOOP.

cl_demo_output=>display( sorted_tab ).


You see the flight data sorted ascending and descending by the longitudes and latitudes of the departure and arrival cities.





If you don't need the data later, declaring and filling an explicit helper table sorted_tab is not necessary in modern times. Therefore, let's put it together.

Putting it Together


The following coding shows the same virtual sorting as above in one single statement.
cl_demo_output=>new(

)->next_section(
`Ascending Sort by Latitude, Longitude of CITYFROM, CITYTO`

)->write( VALUE flights(
FOR <idx>
IN cl_abap_itab_utilities=>virtual_sort(
im_virtual_source =
VALUE #(
( source = REF #( from_city_tab )
components =
VALUE #( ( name = 'latitude' )
( name = 'longitude' ) ) )
( source = REF #( to_city_tab )
components =
VALUE #( ( name = 'latitude' )
( name = 'longitude' ) ) )
( source = REF #( flight_tab )
components =
VALUE #( ( name = 'carrid' )
( name = 'connid' ) ) ) ) )
( flight_tab[ <idx> ] ) )

)->next_section(
`Descending Sort by Latitude, Longitude of CITYFROM, CITYTO`

)->write( VALUE flights(
FOR <idx>
IN cl_abap_itab_utilities=>virtual_sort(
im_virtual_source =
VALUE #(
( source = REF #( from_city_tab )
components =
VALUE #( ( name = 'latitude'
descending = abap_true )
( name = 'longitude'
descending = abap_true ) ) )
( source = REF #( to_city_tab )
components =
VALUE #( ( name = 'latitude'
descending = abap_true )
( name = 'longitude'
descending = abap_true ) ) )
( source = REF #( flight_tab )
components =
VALUE #( ( name = 'carrid' )
( name = 'connid' ) ) ) ) )
( flight_tab[ <idx> ] ) )

)->display( ).

Now the virtual sorting with the method VIRTUAL_SORT of class CL_ABAP_ITAB_UTILITIES takes place at the operand position of a FOR expression for a table iteration. The temporary result of the sorting is used to construct a sorted internal table from the lines of flight_tab. This table is also only temporary and is an input parameter of the method WRITE of class CL_DEMO_OUTPUT.



The sorting in ascending order and in descending order does not change the order of the lines in the internal tables that are involved. These remain in their original unsorted state.

Bottom Line


Virtual sorting makes it possible to generate various sorted output data without affecting the original data.

 

 
20 Comments