TAW12_1 - ABAP Workbench Concept

January 9, 2017 | Author: manikandanu1 | Category: N/A
Share Embed Donate


Short Description

Download TAW12_1 - ABAP Workbench Concept...

Description

TAW12_1 ABAP Workbench Concepts - Part 1

.

.

PARTICIPANT HANDBOOK INSTRUCTOR-LED TRAINING . Course Version: 10 Course Duration: 5 Day(s) Material Number: 50117660

SAP Copyrights and Trademarks © 2013 SAP AG. All rights reserved.

No part of this publication may be reproduced or transmitted in any form or for any purpose without the express permission of SAP AG. The information contained herein may be changed without prior notice. Some software products marketed by SAP AG and its distributors contain proprietary software components of other software vendors. ●

Microsoft, Windows, Excel, Outlook, and PowerPoint are registered trademarks of Microsoft Corporation.



IBM, DB2, DB2 Universal Database, System i, System i5, System p, System p5, System x, System z, System z10, System z9, z10, z9, iSeries, pSeries, xSeries, zSeries, eServer, z/VM, z/OS, i5/OS, S/390, OS/390, OS/400, AS/400, S/390 Parallel Enterprise Server, PowerVM, Power Architecture, POWER6+, POWER6, POWER5+, POWER5, POWER, OpenPower, PowerPC, BatchPipes, BladeCenter, System Storage, GPFS, HACMP, RETAIN, DB2 Connect, RACF, Redbooks, OS/2, Parallel Sysplex, MVS/ESA, AIX, Intelligent Miner, WebSphere, Netfinity, Tivoli and Informix are trademarks or registered trademarks of IBM Corporation.



Linux is the registered trademark of Linus Torvalds in the U.S. and other countries.



Adobe, the Adobe logo, Acrobat, PostScript, and Reader are either trademarks or registered trademarks of Adobe Systems Incorporated in the United States and/or other countries.



Oracle is a registered trademark of Oracle Corporation



UNIX, X/Open, OSF/1, and Motif are registered trademarks of the Open Group.



Citrix, ICA, Program Neighborhood, MetaFrame, WinFrame, VideoFrame, and MultiWin are trademarks or registered trademarks of Citrix Systems, Inc.



HTML, XML, XHTML and W3C are trademarks or registered trademarks of W3C®, World Wide Web Consortium, Massachusetts Institute of Technology.





Java is a registered trademark of Sun Microsystems, Inc. JavaScript is a registered trademark of Sun Microsystems, Inc., used under license for technology invented and implemented by Netscape.



SAP, R/3, SAP NetWeaver, Duet, PartnerEdge, ByDesign, SAP BusinessObjects Explorer, StreamWork, and other SAP products and services mentioned herein as well as their respective logos are trademarks or registered trademarks of SAP AG in Germany and other countries.



Business Objects and the Business Objects logo, BusinessObjects, Crystal Reports, Crystal Decisions, Web Intelligence, Xcelsius, and other Business Objects products and services mentioned herein as well as their respective logos are trademarks or registered trademarks of Business Objects Software Ltd. Business Objects is an SAP company.



Sybase and Adaptive Server, iAnywhere, Sybase 365, SQL Anywhere, and other Sybase products and services mentioned herein as well as their respective logos are trademarks or registered trademarks of Sybase, Inc. Sybase is an SAP company.

All other product and service names mentioned are the trademarks of their respective companies. Data contained in this document serves informational purposes only. National product specifications may vary.

These materials are subject to change without notice. These materials are provided by SAP AG and its affiliated companies ("SAP Group") for informational purposes only, without representation or warranty of any kind, and SAP Group shall not be liable for errors or omissions with respect to the materials. The only warranties for SAP Group products and services are those that are set forth in the express warranty statements accompanying such products and services, if any. Nothing herein should be construed as constituting an additional warranty.

© Copyright . All rights reserved.

iii

iv

© Copyright . All rights reserved.

About This Handbook This handbook is intended to complement the instructor-led presentation of this course, and serve as a source of reference. It is not suitable for self-study. Typographic Conventions American English is the standard used in this handbook. The following typographic conventions are also used.

This information is displayed in the instructor’s presentation

Demonstration

Procedure

Warning or Caution

Hint

Related or Additional Information

Facilitated Discussion

User interface control

Example text

Window title

Example text

© Copyright . All rights reserved.

v

vi

© Copyright . All rights reserved.

Contents xi

Course Overview

1

Unit 1:

Introduction to Object-Oriented Programming

2 13

Lesson: Explaining the Object-Oriented Programming Model Lesson: Analyzing and Designing with Unified Modeling Language (UML)

25

Exercise 1: Create UML Diagrams

35

Unit 2:

37 51 58 65 69 75 81 85 92 95 113

Lesson: Creating Local Classes Exercise 2: Create Local Classes Lesson: Creating and Working with Objects Exercise 3: Create Objects Lesson: Accessing Methods and Attributes Exercise 4: Call Methods Lesson: Implementing Constructors in Local Classes Exercise 5: Create and Use Constructors Lesson: Implementing Class Constructors in Local Classes Exercise 6: Create and Use Static Constructors Unit 3:

114 123 134 137 142 147 154 157 175 176 181 191 195 202 205

Fundamental Object-Oriented Syntax

Inheritance and Casting Lesson: Implementing Inheritance Exercise 7: Implement Inheritance Lesson: Implementing Up-Casts Using Inheritance Exercise 8: Implement Up-Casts Lesson: Implementing Polymorphism Using Inheritance Exercise 9: Implement Polymorphism Using Inheritance Lesson: Implementing Down-Casts Using Inheritance Exercise 10: Implement Down-Casts

Unit 4:

Interfaces and Casting Lesson: Defining and Implementing Local Interfaces Exercise 11: Define and Implement a Local Interface Lesson: Implement Polymorphism Using Interfaces Exercise 12: Implement Polymorphism Using Interfaces Lesson: Joining Classmodels Using Interfaces Exercise 13: Integrate Class Models Using Interfaces

© Copyright . All rights reserved.

vii

223

Unit 5:

224 233 246

Lesson: Implementing Events in Local Classes Exercise 14: Implement Events in Local Classes Lesson: Implementing Events in Local Interfaces

247

Exercise 15: Implement Event Handling for Interfaces

261

Unit 6:

Object-Oriented Repository Objects

262 273 280

Lesson: Creating Global Classes Exercise 16: Implement a Global Class Lesson: Defining and Implementing Global Interfaces

285 294 301

Exercise 17: Import and Implement a Global Interface Lesson: Implementing Inheritance in Global Classes Exercise 18: Implement Inheritance in Global Classes

311

Unit 7:

312 319 325 334 345

387

Unit 8:

448 467

Object-Oriented Design Patterns Lesson: Implementing Special Object-Oriented Techniques Lesson: Implementing the Singleton Pattern Exercise 21: Implement the Singleton Pattern Lesson: Implementing Factory Classes Using Friendship Exercise 22: Implement a Factory Class Using Friendship

Unit 9:

388 395 403 418 427 447

ABAP Object-Oriented Examples Lesson: Implementing ABAP List Viewer (ALV) Exercise 19: Implement the ALV Grid Control Exercise 20: Implement a Popup with the ALV Grid Control Lesson: Implementing Business Add-Ins (BAdIs)

346 354 359 368 371

viii

Object-Oriented Events

Object-Oriented Exception Handling Lesson: Explaining Class-Based Exception Handling Lesson: Defining and Raising Exceptions Exercise 23: Implement Class-Based Exceptions Lesson: Implementing Advanced Exception Handling Techniques Exercise 24: Map Exceptions to Each Other

Unit 10:

Program Calls and Memory Management Lesson: Using Shared Objects Exercise 25: Use Shared Objects

© Copyright . All rights reserved.

477

Unit 11:

Dynamic Programming

478 485

Lesson: Using Generic Data Types Exercise 26: Use Dynamically Typed Field Symbols in Dynamic SQL Statements

495 504

Exercise 27: Access Structure Components Dynamically Lesson: Describing Data Types, Data Objects, and Objects at Runtime Exercise 28: Provide Column Headers Using Runtime Type Identification Lesson: Creating Data Types, Data Objects, and Objects at Runtime Exercise 29: Create Data Objects at Runtime Exercise 30: Create Data Types at Runtime with Runtime Type Creation (RTTC)

517 528 535 545

© Copyright . All rights reserved.

ix

x

© Copyright . All rights reserved.

Course Overview TARGET AUDIENCE This course is intended for the following audiences: ●

Development Consultant



Technology Consultant



Developer

© Copyright . All rights reserved.

xi

xii

© Copyright . All rights reserved.

UNIT 1

Introduction to Object-Oriented Programming

Lesson 1 Explaining the Object-Oriented Programming Model

2

Lesson 2 Analyzing and Designing with Unified Modeling Language (UML) Exercise 1: Create UML Diagrams

13 25

UNIT OBJECTIVES ●

Differentiate between procedural and object-oriented programming models



Describe ABAP Objects



Classify objects



Model objects and classes in UML

© Copyright . All rights reserved.

1

Unit 1 Lesson 1 Explaining the Object-Oriented Programming Model

LESSON OVERVIEW This lesson provides an overview of the key concepts of ABAP programming using the objectoriented model. Business Example You need to explain the object-oriented programming model and its advantages to your development project manager. For this reason, you require the following knowledge: ●

An understanding of procedural and object-oriented programming



An understanding of ABAP objects

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Differentiate between procedural and object-oriented programming models



Describe ABAP Objects

History of Selected Programming Languages

Figure 1: History of Selected Programming Languages

2

© Copyright . All rights reserved.

Lesson: Explaining the Object-Oriented Programming Model

As you can see from the figure, object-oriented programming (like the Simula 67 programming language), and the logical and procedural programming models (as used in languages like C and Pascal), were developed at about the same time. Previously, COBOL and the procedural programming model dominated enterprise application development. SAP used a macro assembler before ABAP was created. Even today, many developers have more experience with procedural programming than with object-oriented programming. Therefore, this introduction references the procedural model when it explains object-oriented programming. ABAP was created to improve reporting. It was independently developed as an in-house programming language. It was influenced by other programming languages like COBOL and Pascal. ABAP was then extended to form ABAP Objects. Therefore, ABAP Objects unites objectoriented and procedural elements in one programming language. For the object-oriented programming part, ABAP Objects adopted object-oriented concepts for enterprise application development in other languages (for example, Java, C++, and Smalltalk).

The Procedural Programming Model

Figure 2: Characteristics of the Procedural Programming Model

Global variables for a program contain data, while subroutines contain functions. Every subroutine can access all global variables.

© Copyright . All rights reserved.

3

Unit 1: Introduction to Object-Oriented Programming

Components of a Procedural ABAP Program

Figure 3: Typical Procedural ABAP Program

A typical procedural ABAP program consists of type definitions and data declarations. The data declarations describe the data structure the program uses when being executed. It is possible to encapsulate logic in modularization units (for example, subroutines or function modules). However, at the main program level, there is no special protection for the global data objects. It is possible to read and change global variables from anywhere in the program. Encapsulation of Data Using Function Groups

Figure 4: Encapsulating Data Using Function Groups

4

© Copyright . All rights reserved.

Lesson: Explaining the Object-Oriented Programming Model

When a function module is called in the main program, its function group is loaded into the internal session. The function group remains active until the main program finishes executing. The system stores the main program and the called function groups in separate memory areas. Even if the data objects of the function groups have the same data object names as they do in the calling program, they do not share the same memory space. Nothing is shared, even if the data objects of the function groups have the same name. It is not possible to access the global data of a function group directly from the main program. You can only call the function modules of the function groups from the main program. In turn, the function modules can access other components, particularly the global data of their own function group. Encapsulation also uses the idea that the implementation of a service can be hidden from other components of the system. The reason for this is that the other components cannot and do not need to make assumptions about the internal status of the modularization unit. In this way, the design of these other components is not dependent on the other modularization units being implemented in a specific way. A function group brings together data and functions which manage the data. Encapsulated access to data and services is one of the many concepts of the object-oriented programming model. Therefore, this programming model and the procedural part of ABAP Objects support this encapsulation. When implementing the Business Application Programming Interface (BAPI), BAPIs are implemented as function modules and Business Objects are implemented as function groups. Function Groups

Figure 5: Example of a Function Group

The fictional function group S_VEHICLE provides a user or client with the services Inc_speed, dec_speed, and get_speed. These services are the interface of the function group. They all have access to the global data object speed, which belongs to the function group.

© Copyright . All rights reserved.

5

Unit 1: Introduction to Object-Oriented Programming

Example of Using the Function Group

Figure 6: Example of Using the Function Group

The main program cannot access the data object speed of the function group directly.

Multiple Instantiation

Figure 7: Several Instances of One Function Group

In order for the main program to work with several vehicles, there must be additional programming and administrative effort. A function group can only refer to one vehicle at a time.

6

© Copyright . All rights reserved.

Lesson: Explaining the Object-Oriented Programming Model

Multiple Instantiation in Object-Oriented Programming

Figure 8: Multiple Instantiation in Object-Oriented Programming

The possibility to create several runtime instances using the same program context is one of the key characteristics of object-oriented programming. In this example, you will develop a program to create four vehicles, all of which have different characteristics. However, all the vehicles share the same data structure and the same set of functions. They all have the ability to protect their data from outside access. ABAP Main Memory and Encapsulation

Figure 9: ABAP Main Memory and Encapsulation

The features of encapsulation using function groups and subroutines are as follows: You use modularization units to encapsulate functions and data.





You can work with the global data of the main program.

© Copyright . All rights reserved.

7

Unit 1: Introduction to Object-Oriented Programming

The features of encapsulation using objects are as follows: ● You can use objects to encapsulate functions and data. ●

You can create multiple instances (objects).

You can perform multiple instantiation. Objects are stored in the same internal session as the program in use. All data areas are separate from each other, which keeps them protected. Data Management in Procedural and Object-Oriented Models

Figure 10: Data Management in Procedural and Object-Oriented Models

Unlike in procedural programming, using multiple instantiation in object-oriented programming allows you to create a direct abstraction of a real object. Encapsulation was systematically extended in this programming model.

ABAP Objects The object-oriented concepts of ABAP Objects share concepts with other modern objectoriented languages like C++ or Java. Concepts that proved to be unsuccessful in other languages were not included in ABAP Objects. On the other hand, ABAP Objects has helpful language elements that C++ and Java do not have. Certain features of ABAP Objects only exist because of the guaranteed upward compatibility of older ABAP language elements. The difference in ABAP Objects compared to other object-oriented languages are in the development environment. You can use the entire range of functions of the ABAP Workbench with ABAP Objects. You can use ABAP Objects statements in procedural ABAP programs.

8

© Copyright . All rights reserved.

Lesson: Explaining the Object-Oriented Programming Model

ABAP Objects as a Compatible Extension of ABAP

Figure 11: ABAP Objects as a Compatible Extension of ABAP

ABAP Objects is not a new language, but it was designed as a systematic extension of ABAP. All of the extensions, including the old procedural parts, are upwardly compatible. Type checks in the object-oriented contexts of ABAP Objects are stricter than those in the procedural contexts. To develop ABAP Objects, SAP cleaned up the ABAP language in the object-oriented contexts. This means that obsolete statements lead to syntax errors.

Note: However, it is also advisable to avoid obsolete statements in the purely procedural environment, since it creates safer and more flexible source code. Nevertheless, because the language is upwardly compatible, it is not possible to prevent the use of such statements entirely. For a list of obsolete language elements, refer to the ABAP keyword documentation. ABAP prohibits the use of obsolete statements in the object-oriented context.

© Copyright . All rights reserved.

9

Unit 1: Introduction to Object-Oriented Programming

Client/Server Relationship Between Objects

Figure 12: Client/Server Relationships Between Objects

Objects behave like client/server systems. When one object sends a message to another object to ask it to behave in a certain way, the first object is defined as a client and the second object is defined as a server. To be able to separate requests and deliveries of services, the following conditions must be met: ● The client object must adhere to the protocol of the server object. ●

The protocol of server object must be clear enough for a potential client to follow it without any problems.

Objects can perform both roles simultaneously. They can offer services to other objects while requesting services at the same time. In object-oriented programming, the services are distributed among the objects in such a way that there are no redundancies and each object offers exactly those services it is responsible for. If an object needs any other services, it requests them from other objects. This concept is known as the principle of delegation. Client/Server Relationship – Example The developer should implement the common task of data retrieval and output over at least two objects. One object is responsible for data retrieval and another object is responsible for output. As long as the data retrieval object does not change its protocol, the developer can alter the retrieval object’s internal implementation without changing the other object. Alternatively, a different object could even replace the data retrieval object as long as the new object uses the same protocol. These exchanges can also take place at runtime.

10

© Copyright . All rights reserved.

Lesson: Explaining the Object-Oriented Programming Model

Additional Concepts of the Object-Oriented Programming Model

Figure 13: Additional Concepts of the Object-Oriented Programming Model

Some additional concepts in the object-oriented programming model are as follows: ● Inheritance Inheritance defines the implementation relationships between classes, so that one class (subclass) adopts, adapts, or extends the structure and behavior of another class (superclass). ●

Polymorphism Polymorphism is when instances of classes respond differently to the same messages.



Event control Instead of sending messages directly to specific objects, objects can also trigger events. The objects react when the event is triggered.

Features of Object-Oriented ABAP The key characteristics of the object-oriented programming model of ABAP Objects are as follows: ●

Objects are a direct abstraction of the real world.



Objects are units made up of data and functions.



Processes can be implemented in a better way than in procedural programming.

The advantages of the object-oriented programming model compared to the procedural programming model are as follows:

© Copyright . All rights reserved.

11

Unit 1: Introduction to Object-Oriented Programming



Improved software structure and consistency in the development process



Reduced maintenance effort and less susceptibility to errors



Better integration of the customer or user into the analysis, design, and maintenance process



Simpler and more secure extension of the software

A standardized language is used in the various phases of software development (analysis, specification, design, and implementation). Because of this standardization, communication is easier when you change between phases. The Software Development Process

Figure 14: The Software Development Process

In object-oriented programming, analysis and design decisions have a greater effect on the implementation than they have on procedural programming. Therefore, you should use modeling language or tools to standardize the analysis and design phase. LESSON SUMMARY You should now be able to:

12



Differentiate between procedural and object-oriented programming models



Describe ABAP Objects

© Copyright . All rights reserved.

Unit 1 Lesson 2 Analyzing and Designing with Unified Modeling Language (UML)

LESSON OVERVIEW This lesson explains how to develop an object-oriented solution to a business application problem. It also explains how to classify your objects and define the relationships between them using parts of Unified Modeling Language (UML) as a visual aid. Business Example You need to model a business application requirement before you implement the business application. For this reason, you require the following knowledge: ●

An understanding of class diagrams



An understanding of object diagrams



An understanding of sequence diagrams

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Classify objects



Model objects and classes in UML

© Copyright . All rights reserved.

13

Unit 1: Introduction to Object-Oriented Programming

Classifying Objects

Figure 15: Classifying Objects

Object-oriented programming views the real world as a collection of objects-like airplanes, cars, and people. Some of these objects are similar. In other words, objects can be described in the same way if they use the same characteristics and exhibit the same behavior. You can group all the characteristics and behaviors of these similar objects into one central class. This class is used to describe every object derived from it. Therefore, a class is a description of a quantity of objects that exhibit the same characteristics and the same behavior. For example, the vehicle (make x, ..., series n), is an object of class car. This object is a concrete instance of its class. Therefore, an object has an identity, a status (number of characteristic instances), and a behavior. The concepts of identity and status are different from one another. Identity is an attribute that distinguishes each object from all the other objects in its class. Two objects can have identical attribute values, but these objects may not be identical . For example, two coffee cups have the same height, diameter, handle, and color. Although their statuses are completely identical, they are two different coffee cups. Literature on the subject of object oriented programming talks about instances. The term instance means an object.

Note: The literal meaning of instance is slightly more specific. It means that the instance of a class is uniquely identifiable. In this chapter, you will make a distinction between instance and object.

14

© Copyright . All rights reserved.

Lesson: Analyzing and Designing with Unified Modeling Language (UML)

Classes as Abstraction Forms

Figure 16: Classes as Abstraction Forms

In a software context, abstractions are simplifications of complex relationships in the real world. You can abstract a real, existing object to the dimensions needed to simulate a certain section of the real world. In the figure, vehicles are used to explain the concept of abstraction. Software for a vehicle enthusiast and software for a scrap merchant contain different abstractions (classes) for objects. Therefore, depending on the type of abstraction, a class can contain different aspects of an object. Comparing Classes and Objects

Figure 17: Comparing Classes and Objects

© Copyright . All rights reserved.

15

Unit 1: Introduction to Object-Oriented Programming

An understanding of the relationship between classes and objects is a prerequisite for completing the following lessons successfully. Modeling in UML UML is a globally standardized modeling language. You use it for the specification, construction, visualization, and documentation of software system models. UML enables uniform communication between users. UML is an industry standard and was developed by the Object Management Group (OMG) in September 1997. SAP uses UML as the company-wide standard for object-oriented modeling. For more information on the UML specifications, see http://www.omg.org on the OMG homepage.

UML Diagrams The different diagram types in UML represent different views of a system. Three important diagram types that represent different views of a system are as follows: ●

Class diagrams Class diagrams show the relationships between the classes. This is a static view of a model.



Behavior diagrams Behavior diagrams show the sequence in which the objects relate to each other.



Component diagrams Component diagrams show the organization and dependencies of components.

You can use ABAP Objects to implement class diagrams and behavior diagrams from a programming perspective. Component diagrams can be realized using the repository object package. For example, you can bundle software components into packages according to the structure’s specification in a Component diagram.

16

© Copyright . All rights reserved.

Lesson: Analyzing and Designing with Unified Modeling Language (UML)

UML Representation of a Class

Figure 18: Representation of a Class

A class is represented by a rectangle in UML notation. A class can be represented as follows: ● Name of the class ●

Attributes of the class (optional)



Methods of the class (optional)

Attributes describe the data that can be stored in the objects of a class. They also determine the status of an object. Methods describe the functions an object can perform. They determine how an object behaves. Example of a Class Diagram

Figure 19: An Example of a Class Diagram

A class diagram describes all static relationships between the classes.

© Copyright . All rights reserved.

17

Unit 1: Introduction to Object-Oriented Programming

The basic forms of static relationships are as follows: ● Association A customer books a car at a rental car company. ●

Generalization and Specialization A car, a bus, and a truck are all vehicles.

Note: Classes can also be shown in class diagrams with their attributes and methods. In this example of a class diagram, these attributes and methods have been omitted to improve clarity. Association

Figure 20: Association

An association describes a semantic relationship between classes. The specific relationship between objects in these classes is known as an object link. Therefore, object links indicate associations. However, an association can also be recursive. In that case, the class would have a relationship with itself. In most cases, recursive associations are used to link two different objects in the same class. Each association has two roles--one for each direction of the association. Each role can be described by an association name. Each role has a cardinality that shows how many instances can participate in this relationship. The multiplicity is the number of participating objects in one class that have a relationship to an object in the other class. Like all other elements of the model, cardinalities are dependent on the concrete situation being modeled.

18

© Copyright . All rights reserved.

Lesson: Analyzing and Designing with Unified Modeling Language (UML)

In this example, you could also require a cardinality of at least one to indicate that only someone who actually makes a booking becomes a customer of the rental car company. On the other hand, the cardinality of any number would allow for a more general definition of a customer. Characteristics of association are as follows: ● You must represent an association between class symbols by drawing a line between them. ●







You must specify the cardinality (also referred to as multiplicity) of the relationship at the end of each line. You must use arrows to indicate the navigation options. You must write the association name in italics above the line. The name may contain an arrow to indicate the read direction. Enter the role names at the end of the lines if the modeler defines roles for both partners.

Association with Roles -  Example

Figure 21: Examples of Association with Roles

You can use role names at the end of the of the association lines to describe the relationships between the classes involved. In the example, a person could appear in the role of an employee or in the role of a company director, for example. In the recursive association shown in the example, the roles of child and parent are defined using role names. Two instances of the LCL_PERSON class have a relationship with each other and represent two roles.

© Copyright . All rights reserved.

19

Unit 1: Introduction to Object-Oriented Programming

Association Classes

Figure 22: Association Classes

If association is used to link two classes, then a special class can represent this relationship. The characteristics of the relationship are described using the attributes of the association class. A dotted line connects this class to the association line. Aggregation and Composition

Figure 23: Aggregation and Composition

Aggregation and composition are specializations of association. Aggregation and composition show that an object can contain other objects. The relationship can be described using the phrases “consists of” or “is a part of”. For example, a car consists of wheels and an engine among other things.

20

© Copyright . All rights reserved.

Lesson: Analyzing and Designing with Unified Modeling Language (UML)

Aggregation and composition appear as a line between two classes. They are labelled using a small rhombus. The rhombus indicates the aggregation or composition. Otherwise, the notation conventions are the same used for associations. Composition is a specialization of aggregation. Composition means the contained object cannot exist without the aggregation (for example, a car reservation cannot exist without the car rental agency). Therefore, the cardinality of this kind of aggregate is at least one. The lifetime of the individual parts is linked to the lifetime of the aggregate. This means parts are created either at the same time as the aggregate or after the aggregate, and are destroyed either at the same time as the aggregate or before the aggregate. In UML notation, a filled-in rhombus denotes composition. Generalization and Specialization

Figure 24: Generalization and Specialization

Generalization and specialization relationships are always bidirectional. For example, the class lcl_truck can be generalized as a special class of lcl_vehicle. Generalization and specialization relationships are denoted by a triangular arrow. This arrow always points from the specialized class to the generalized class. The level of generalization increases in the direction of the arrow. Trees can be built up using these relationships.

© Copyright . All rights reserved.

21

Unit 1: Introduction to Object-Oriented Programming

Object Diagram

Figure 25: An Object Diagram

An object diagram is a snapshot taken during program execution. It describes instances of classes and the relationships between them. It is not a new type of diagram, but rather a variant of the class diagram. It is only useful for representing a complex class diagram.

Sequence Diagram

Figure 26: A Sequence Diagram

Sequence diagrams are used to show certain processes or situations. A sequence diagram describes the sequence in which objects are processed and the interaction they have with each other.

22

© Copyright . All rights reserved.

Lesson: Analyzing and Designing with Unified Modeling Language (UML)

Sequence diagrams may show the following processes: ● When objects are created or deleted ●

When objects exchange messages

In UML notation, the object lifeline is represented by dotted vertical lines with a box containing the object name at the top. An X is used to indicate the end of the lifeline. The control focus appears as a vertical rectangle on the object lifeline. The control focus shows the active period of the object. Possible statuses of an object are as follows: ●

An object is active when actions are executed.



An object is indirectly active if it is waiting for a subordinate procedure to end.

Messages appear as horizontal arrows between the object lines. The message is written above the arrow in the Message (parameter) form. There are various ways to represent the reply. In this example, it appears as a dotted returning arrow. You can also include a description of the process and add comments to the object lifeline. The Delegation Principle

Figure 27: Delegation Principle in Sequence Diagram

In delegation, two objects are involved in handling a request. The recipient of the request assigns the execution of the request to a delegate. In this example, the driver (object driver) sends the message get_fuel_level ( ) to the vehicle (object car). When the message is received, the car sends a message to the tank (object tank) to find out what the tank contains. In other words, the car delegates the task to the tank. If necessary, the car formats the information containing the current value of the contents of the tank before passing it back to the driver.

© Copyright . All rights reserved.

23

Unit 1: Introduction to Object-Oriented Programming

24

© Copyright . All rights reserved.

Unit 1 Exercise 1 Create UML Diagrams

Business Example You are a modeler for an airline corporation that owns several airline carriers. You need to create a simple model to manage your airline carriers and airplanes. For this reason, you must be able to design simple UML class diagrams and model the basic objects. In this airplane management model, you need to create relevant classes with attributes and methods, and define the association between classes using suitable association types and cardinalities. Task 1 1. Create a UML class diagram containing the following classes: Class Name

Description

LCL_CARRIER

For the Airline Companies

LCL_AIRPLANE

For the Airline Companies

LCL_PASSENGER_PLANE

For Passenger Planes

LCL_CARGO_PLANE

For Cargo Planes

2. Create appropriate attributes and methods for each class. 3. Define relationships between your classes and choose suitable association types. 4. Choose suitable cardinalities. Task 2 As a modeler, decide whether the object diagrams in this unit are correct. 1. The figure shows a class diagram. Eight object diagrams are drawn for this class diagram. Decide whether each object diagram is correct and mark the corresponding checkbox to indicate your answer.

© Copyright . All rights reserved.

25

Unit 1: Introduction to Object-Oriented Programming

Figure 29: Possible Object Diagrams (1)

See more diagrams in the figure (Possible Object Diagrams (2).

Figure 30: Possible Object Diagrams (2)

26

© Copyright . All rights reserved.

Unit 1 Solution 1 Create UML Diagrams

Business Example You are a modeler for an airline corporation that owns several airline carriers. You need to create a simple model to manage your airline carriers and airplanes. For this reason, you must be able to design simple UML class diagrams and model the basic objects. In this airplane management model, you need to create relevant classes with attributes and methods, and define the association between classes using suitable association types and cardinalities. Task 1 1. Create a UML class diagram containing the following classes: Class Name

Description

LCL_CARRIER

For the Airline Companies

LCL_AIRPLANE

For the Airline Companies

LCL_PASSENGER_PLANE

For Passenger Planes

LCL_CARGO_PLANE

For Cargo Planes

a) Use the model solution as a guide. 2. Create appropriate attributes and methods for each class. a) Be sure to define the general attributes and methods for airplanes in LCL_AIRPLANE. b) Use the model solution as a guide for the attributes and methods for all of the classes required. 3. Define relationships between your classes and choose suitable association types. a) A generalization and specialization relationship between LCL_AIRPLANE and LCL_PASSENGER_PLANE or LCL_CARGO_PLANE seems to be appropriate. Create an aggregation between LCL_AIRPLANE and LCL_CARRIER. b) Use the model solution as a guide. 4. Choose suitable cardinalities. a) You can use various cardinalities in this case. Use the relevant sections of the lesson and the model solution as a guide.

© Copyright . All rights reserved.

27

Unit 1: Introduction to Object-Oriented Programming

Figure 28: Class Diagram for Exercise - CARRIER/AIRPLANE

Task 2 As a modeler, decide whether the object diagrams in this unit are correct. 1. The figure shows a class diagram. Eight object diagrams are drawn for this class diagram. Decide whether each object diagram is correct and mark the corresponding checkbox to indicate your answer.

28

© Copyright . All rights reserved.

Lesson: Analyzing and Designing with Unified Modeling Language (UML)

Figure 29: Possible Object Diagrams (1)

See more diagrams in the figure (Possible Object Diagrams (2).

Figure 30: Possible Object Diagrams (2)

a) The object diagrams numbered 2, 4, 5, 6, and 8 are correct.

© Copyright . All rights reserved.

29

Unit 1: Introduction to Object-Oriented Programming

LESSON SUMMARY You should now be able to:

30



Classify objects



Model objects and classes in UML

© Copyright . All rights reserved.

Unit 1 Learning Assessment

1. Data and functions are kept separate in the procedural programming model. Determine whether this statement is true or false. X

True

X

False

2. When the main program calls a function module, only this function module is loaded into the internal session. Determine whether this statement is true or false. X

True

X

False

3. What does multiple instantiation mean? Choose the correct answer. X

A Creating and managing runtime instances

X

B Implementing relationships between classes

X

C Creating instances of different classes

X

D Sending messages directly to specific objects by triggering events

4. Which of the following describes how instances of different classes respond differently to the same messages? Choose the correct answer. X

A Inheritance

X

B Polymorphism

X

C Encapsulation

X

D Event control

© Copyright . All rights reserved.

31

Unit 1: Learning Assessment

5. Which of the following is a simplification of complex relationships in the real world? Choose the correct answer. X

A Inheritance

X

B Abstraction

X

C Encapsulation

X

D Event control

6. The ______________ diagram pays particular attention to the sequence in which the objects relate to each other. Choose the correct answer. X

A class

X

B behavior

X

C component

X

D object

7. You can group all characteristics and behaviors of similar objects into one central class. Determine whether this statement is true or false.

32

X

True

X

False

© Copyright . All rights reserved.

Unit 1 Learning Assessment - Answers

1. Data and functions are kept separate in the procedural programming model. Determine whether this statement is true or false. X

True

X

False

2. When the main program calls a function module, only this function module is loaded into the internal session. Determine whether this statement is true or false. X

True

X

False

3. What does multiple instantiation mean? Choose the correct answer. X

A Creating and managing runtime instances

X

B Implementing relationships between classes

X

C Creating instances of different classes

X

D Sending messages directly to specific objects by triggering events

© Copyright . All rights reserved.

33

Unit 1: Learning Assessment - Answers

4. Which of the following describes how instances of different classes respond differently to the same messages? Choose the correct answer. X

A Inheritance

X

B Polymorphism

X

C Encapsulation

X

D Event control

5. Which of the following is a simplification of complex relationships in the real world? Choose the correct answer. X

A Inheritance

X

B Abstraction

X

C Encapsulation

X

D Event control

6. The ______________ diagram pays particular attention to the sequence in which the objects relate to each other. Choose the correct answer. X

A class

X

B behavior

X

C component

X

D object

7. You can group all characteristics and behaviors of similar objects into one central class. Determine whether this statement is true or false.

34

X

True

X

False

© Copyright . All rights reserved.

UNIT 2

Fundamental Object-Oriented Syntax

Lesson 1 Creating Local Classes Exercise 2: Create Local Classes

37 51

Lesson 2 Creating and Working with Objects Exercise 3: Create Objects

58 65

Lesson 3 Accessing Methods and Attributes Exercise 4: Call Methods

69 75

Lesson 4 Implementing Constructors in Local Classes Exercise 5: Create and Use Constructors

81 85

Lesson 5 Implementing Class Constructors in Local Classes Exercise 6: Create and Use Static Constructors

92 95

UNIT OBJECTIVES ●

Define local classes



Define attributes



Create methods



Create objects



Handle objects



Call instance methods

© Copyright . All rights reserved.

35

Unit 2: Fundamental Object-Oriented Syntax

36



Call static methods



Call functional methods



Access public attributes



Create and use constructors



Create and use static constructors

© Copyright . All rights reserved.

Unit 2 Lesson 1 Creating Local Classes

LESSON OVERVIEW This lesson provides an overview of local classes, attributes, and methods, which are the fundamental object-oriented syntax elements. Business Example As a developer, you need to implement classes, objects, and associations of your model in ABAP Objects. LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Define local classes



Define attributes



Create methods

Definition of Local Classes

Figure 31: An Example of a Class

The concept of classes is the foundation of object-oriented programming. A class can either have public components and private components. You can access public components, such as

© Copyright . All rights reserved.

37

Unit 2: Fundamental Object-Oriented Syntax

methods and events, from outside a class. However, you cannot access private components, for example data types and attributes, from outside a class. The figure shows a vehicle as an example of a class. Characteristics of a Class

Figure 32: Defining Classes

Characteristics of a class in object-oriented programming are as follows: A class is a set of objects that have the same structure and exhibit the same behavior.









38

A class provides a blueprint for all objects created in the class. A class is made up of  components, such as attributes, methods, events, constants, types, and implemented interfaces, defined in the definition part. You can implement only methods in the implementation part. A class statement cannot be nested; that is, you cannot define a class within a class. However, you can define local auxiliary classes for global classes.

© Copyright . All rights reserved.

Lesson: Creating Local Classes

Declaration of Class Attributes

Figure 33: An Example of Attributes

Attributes contain the data that can be stored in the objects of a class. The types of class attributes are as follows: ● Elementary ●

Structured



Table-type

Attributes can consist of data types (local or global) or reference types. The following table shows some examples of attributes for class LCL_VEHICLE: Attributes

Description

MAKE

Vehicle make

MODEL

Type of model

SER_NO

Serial number

COLOR

Color

MAX_SEATS

Number of seats

R_MOTOR

Reference to class LCL_MOTOR

© Copyright . All rights reserved.

39

Unit 2: Fundamental Object-Oriented Syntax

Definition of Attributes, Types, and Constants

Figure 34: Definition of Attributes, Types, and Constants

In class DATA statements, you can only use the TYPE addition to refer to data types. The LIKE addition is only allowed for local data objects or SY fields (for example, SY-DATE, SYUNAME, and so on). The READ-ONLY addition indicates that a public attribute declared with DATA can be read from outside. However, the attribute can only be changed by methods in the same class. Currently, you can use the READ-ONLY addition in the public visibility section (PUBLIC SECTION) of a class declaration or in an interface definition. With TYPE REF TO, you can type an attribute as a reference. The CONSTANTS statement is used within the class definition to define data objects that have a constant value. If you use the TYPES statement in the class definition, you are declaring a local type which is specific to this local class. You can create a local type to be used by one or more attributes within the same class.

40

© Copyright . All rights reserved.

Lesson: Creating Local Classes

Visibility of Attributes

Figure 35: Visibility Sections of Attributes

Private attributes cannot be addressed directly from outside the class and are not visible to outside users. You can protect attributes from outside access by characterizing them as private attributes. Note: The friendship concept is an exception to this rule. Public attributes are attributes that are visible to all users and can be directly accessed by outside users. Similarly, the constants and types defined by a class can be either private (for use inside the class), or public, (accessible from outside the class). The public components of a class are collectively known as the class interface. Using the private visibility section is known as information hiding or encapsulation. Encapsulation protects a class user by making changes to private components invisible to the external user. You can change the private components of a class without changing the interface. Assume that the private components of a class are changed at some point with its interface remaining the same, external users can still continue to work with the class as before. The external users can only access the components through the interface of the class and will not notice the internal implementation changes in the PRIVATE SECTIONS. However, when the public components of a class change, every external user must take those changes into account. Therefore, use public attributes sparingly, or avoid making incompatible changes to public components altogether.

© Copyright . All rights reserved.

41

Unit 2: Fundamental Object-Oriented Syntax

Accessing Private Attributes

Figure 36: Accessing Private Attributes

Private attributes are defined in the PRIVATE SECTION of a class. Public attributes are defined in the PUBLIC SECTION of a class. It is syntactically impossible to access private attributes directly from outside. However, you can access private attributes using public methods that return or change the values of the private attributes. The slightly higher runtime requirement (method calls in comparison with direct value assignment) is taken into account to satisfy the encapsulation concept. The signature of a public method clearly establishes which values must or can be transferred, and which types are to be assigned to these values. The signature of a public method forces the external user to use the correct types. This method also ensures that all private attributes are dealt consistently. For the example in the figure, if the MAKE and MODEL attributes are public, it will be quite risky because the user may forget to supply the attributes or specify inconsistent attributes. To implement this situation, you can use a public method, SET_TYPE, to ensure that proper values are specified for both the attributes. A strict syntax check governs method calls, ensuring the transfer of all required parameters. A method can perform a consistency check (to see if a certain vehicle make produces the chosen model) and raise an exception if an error occurs. To minimize runtime, individual attributes can be defined in the public visibility section but you must then give them the READ-ONLY addition.

42

© Copyright . All rights reserved.

Lesson: Creating Local Classes

Static Attributes and Instance Attributes

Figure 37: Comparison of Instance Attributes with Static Attributes

Different kinds of attributes are as follows: ● Instance attributes Instance attributes exist once per object; that is, once per runtime instance of the class. You define instance attributes with the syntax element, DATA. ●

Static attributes Static attributes exist once for each class and are visible for all runtime instances in that class. You define static attributes with the syntax element, CLASS-DATA. Static attributes usually contain the following information that applies to all instances: Types and constants -

Central application data buffers

-

Administrative information, such as the instance counter

Technical literature refers to static attributes as “class attributes” (we use the CLASS-DATA syntax element). As in C++ and Java, ABAP Objects uses the official term “static attribute”.

© Copyright . All rights reserved.

43

Unit 2: Fundamental Object-Oriented Syntax

Instance Attributes and Static Attributes in the Program Context

Figure 38: Instance Attributes and Static Attributes in the Program Context

The figure shows how the N_O_VEHICLES static attribute is related to other program elements in the memory. The static attribute exists only once in the loaded class, regardless of the number of instances of LCL_VEHICLE. Therefore, you can say that instances share static attributes.

Caution: An integer data object is defined to count instances. It is not possible to determine the number of created instances from the system.

44

© Copyright . All rights reserved.

Lesson: Creating Local Classes

Implementation of Methods

Figure 39: Syntax for Methods

Some of the key Characteristics of methods are as follows: ●





Methods are internal procedures in classes that determine the behavior of the objects. They can access all attributes in their class and can therefore change the state of attributes.   Methods have a signature (interface parameters and exceptions) that enables them to receive values when they are called and pass values back to the calling program. Methods can have any number of IMPORTING, EXPORTING, and CHANGING parameters. All parameters can be passed by value or reference.

Method Signature One return value can be defined in the method using the RETURN parameter. When using a RETURNING parameter you cannot use EXPORTING and CHANGING simultaneously. You can also use the RETURNING parameter to define functional methods. You can define all input parameters (IMPORTING and CHANGING parameters) as optional parameters in the declaration using the OPTIONAL or DEFAULT addition. You do not necessarily need to transfer these parameters when you call the object. By using the OPTIONAL addition, the parameter initializes according to type, while the DEFAULT addition allows you to enter a start value. Methods also support the SY-SUBRC return value, but only when you define the signature exceptions with the use of EXCEPTIONS. As of SAP AS 6.10, you can use the RAISING addition in

© Copyright . All rights reserved.

45

Unit 2: Fundamental Object-Oriented Syntax

place of EXCEPTIONS to propagate class-based exceptions. The caller then handles these classbased exceptions without evaluating the SY-SUBRC return value.

Note: Do not use both concepts together in one program.

Visibility of Methods

Figure 40: Visibility Sections of Methods

You assign methods to a visibility section to determine whether methods are called from outside the class or from within the class. Private methods allow internal modularization.

46

© Copyright . All rights reserved.

Lesson: Creating Local Classes

Access to Private Methods

Figure 41: Accessing Private Methods

You define private methods in the PRIVATE SECTION and public methods in the PUBLIC SECTION of a class. It is not possible to directly access private methods from outside. However, a private method can be called by a public method. In the example shown in the figure, INIT_TYPE is a private method that is called by the SET_TYPE public method. Defining this private auxiliary method is useful because the instruction to initialize attributes may be used in other methods.

Note: This is an introductory example. Later, you will learn more programming techniques for evaluating formal parameters. In a class, declarations of attribute names, method names, event names, constant names, type names, and alias names share the same namespace. Additionally there is a local namespace within methods. Local declarations within a method override declarations made in the class.

© Copyright . All rights reserved.

47

Unit 2: Fundamental Object-Oriented Syntax

Static Methods and Instance Methods

Figure 42: Comparison of Instance Methods with Static Methods

Different Kinds of methods are as follows: Instance methods



You define instance methods using the METHODS syntax keyword. ●

Static methods You define static methods using the CLASS-METHODS syntax keyword. You define static methods at class level. However, you can only access static components in the implementation section. This means that static methods do not need instances and can be directly accessed through the class.

In the example shown in the figure, you can only access the N_O_VEHICLES static attribute within the GET_N_O_VEHICLES static method. All other attributes are instance attributes and can only appear within instance methods. Technical literature refers to static methods as “class methods” (compared to the CLASSMETHODS syntax element). In ABAP Objects, the official term is “static method”, as it is in C++ and Java.

48

© Copyright . All rights reserved.

Lesson: Creating Local Classes

Comparison of UML Class Diagram with Implementation

Figure 43: Visibility Sections and UML Notation

A Unified Modeling Language (UML) class diagram lists the class name, class attributes, and methods. The components in a class are shown in a UML  using the following notations: ● Plus sign (+) A plus sign (+) indicates public components (visible to all users). ●

Minus sign (–) A minus sign (–) indicates private components (invisible to outside users).



Underline An underlined component name sign (_) indicates static components.

Alternatively, the keywords public and private can be used as a prefix for methods. A UML also allows manufacturers of modeling tools to create their own symbols for increased visibility. The use of visibility characteristics is optional and is normally used only in models that are nearing implementation.

© Copyright . All rights reserved.

49

Unit 2: Fundamental Object-Oriented Syntax

50

© Copyright . All rights reserved.

Unit 2 Exercise 2 Create Local Classes

Business Example You are a developer for an airline corporation that owns several airline carriers. You need to develop an object-oriented program that can manage airline carriers and their airlines. For this reason, you must be able to define classes, attributes, and methods. Template: None Solution: SAPBC401_BAS_S1 Task 1 Create an executable program without a TOP include (suggested name:ZBC401_##_MAIN where ## is your 2-digit group number). Task 2 Declare and implement a class for airplanes. 1. Within your program, declare the local class LCL_AIRPLANE. 2. Define the following attributes, Attribute Name/description

Data type

Attribute Type

MV_NAME (name of airplane)

STRING

Private instance attribute

MV_PLANETYPE (type of airplane)

SAPLANE-PLANETYPE Private instance attribute

GV_N_O_AIRPLANES (instance counter) I

Private static attribute

3. Define the public instance method SET_ATTRIBUTES for setting private instance attributes. Your method signature must consist of two suitable import parameters defined as compatible with the two attributes. Implement the method in such a way that the two instance attributes are set. 4. Define the public instance method DISPLAY_ATTRIBUTES for displaying private instance attributes. Implement the method in such a way that the values of the two instance attributes are output as an ABAP list. You can also output icons if the ICON type group is loaded.

© Copyright . All rights reserved.

51

Unit 2: Fundamental Object-Oriented Syntax

Hint: To load the type group, use the statement TYPE-POOLS icon.

Note: In adherence to the delegation principle, the reading of attribute values and their output is not implemented in the same method. However, because of time constraints, you can ignore the delegation principle for this exercise. 5. Define the public static method DISPLAY_N_O_AIRPLANES to display the private static attribute. Implement the method in such a way that the value of the static attributes is output in the ABAP list. Note: So far, your class does not have a mechanism for ensuring that the instance counter increases each time an object is created. Decide if you want to omit the counter for now, or if you want to temporarily control increments using the SET_ATTRIBUTES method. 6. To improve the list output, arrange the output in two columns, one for the descriptive text and the other for the attribute values. Hint: Use addition AT of the WRITE statement to place the output in a given column. To facilitate later adjustments, do not use a literal for the number. Define private constant C_POS_1 instead.

52

© Copyright . All rights reserved.

Unit 2 Solution 2 Create Local Classes

Business Example You are a developer for an airline corporation that owns several airline carriers. You need to develop an object-oriented program that can manage airline carriers and their airlines. For this reason, you must be able to define classes, attributes, and methods. Template: None Solution: SAPBC401_BAS_S1 Task 1 Create an executable program without a TOP include (suggested name:ZBC401_##_MAIN where ## is your 2-digit group number). Task 2 Declare and implement a class for airplanes. 1. Within your program, declare the local class LCL_AIRPLANE. a) See the source code extract from the model solution. 2. Define the following attributes, Attribute Name/description

Data type

Attribute Type

MV_NAME (name of airplane)

STRING

Private instance attribute

MV_PLANETYPE (type of airplane)

SAPLANE-PLANETYPE Private instance attribute

GV_N_O_AIRPLANES (instance counter) I

Private static attribute

a) See the source code extract from the model solution. 3. Define the public instance method SET_ATTRIBUTES for setting private instance attributes. Your method signature must consist of two suitable import parameters defined as compatible with the two attributes. Implement the method in such a way that the two instance attributes are set. a) See the source code extract from the model solution. 4. Define the public instance method DISPLAY_ATTRIBUTES for displaying private instance attributes. Implement the method in such a way that the values of the two instance attributes are output as an ABAP list. You can also output icons if the ICON type group is loaded.

© Copyright . All rights reserved.

53

Unit 2: Fundamental Object-Oriented Syntax

Hint: To load the type group, use the statement TYPE-POOLS icon.

Note: In adherence to the delegation principle, the reading of attribute values and their output is not implemented in the same method. However, because of time constraints, you can ignore the delegation principle for this exercise. a) See the source code extract from the model solution. 5. Define the public static method DISPLAY_N_O_AIRPLANES to display the private static attribute. Implement the method in such a way that the value of the static attributes is output in the ABAP list. Note: So far, your class does not have a mechanism for ensuring that the instance counter increases each time an object is created. Decide if you want to omit the counter for now, or if you want to temporarily control increments using the SET_ATTRIBUTES method. a) See the source code extract from the model solution. 6. To improve the list output, arrange the output in two columns, one for the descriptive text and the other for the attribute values. Hint: Use addition AT of the WRITE statement to place the output in a given column. To facilitate later adjustments, do not use a literal for the number. Define private constant C_POS_1 instead. a) See the source code extract from the model solution. Solution: SAPBC401_BAS_S1 REPORT sapbc401_bas_s1. TYPE-POOLS icon. *--------------------------------------------------------* * CLASS lcl_airplane DEFINITION * *--------------------------------------------------------* CLASS lcl_airplane DEFINITION.

54

© Copyright . All rights reserved.

Lesson: Creating Local Classes

PUBLIC SECTION. METHODS: set_attributes IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype, display_attributes. CLASS-METHODS: display_n_o_airplanes. PROTECTED SECTION. PRIVATE SECTION. CONSTANTS: c_pos_1 TYPE i VALUE 30. DATA: mv_name TYPE string, mv_planetype TYPE saplane-planetype. CLASS-DATA: gv_n_o_airplanes TYPE i. ENDCLASS. "lcl_airplane DEFINITION *--------------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION * *--------------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. METHOD set_attributes. mv_name = iv_name. mv_planetype = iv_planetype. * doesn't make sense so much, only in order to get an effect * after calling display_n_o_airplanes: gv_n_o_airplanes = gv_n_o_airplanes + 1. ENDMETHOD. "set_attributes METHOD display_attributes. DATA: lv_weight TYPE saplane-weight, lv_cap TYPE saplane-tankcap. WRITE: / icon_ws_plane AS ICON, / 'Name of Airplane'(001) , AT c_pos_1 mv_name, / 'Type of Airplane:'(002), AT c_pos_1 mv_planetype. ENDMETHOD. "display_attributes METHOD display_n_o_airplanes. SKIP. WRITE: / 'Number of airplanes:'(ca1), AT c_pos_1 gv_n_o_airplanes LEFT-JUSTIFIED.

© Copyright . All rights reserved.

55

Unit 2: Fundamental Object-Oriented Syntax

ENDMETHOD. "display_n_o_airplanes ENDCLASS. "lcl_airplane IMPLEMENTATION

56

© Copyright . All rights reserved.

Lesson: Creating Local Classes

LESSON SUMMARY You should now be able to: ●

Define local classes



Define attributes



Create methods

© Copyright . All rights reserved.

57

Unit 2 Lesson 2 Creating and Working with Objects

LESSON OVERVIEW This lesson explains the concept of creating and handling objects. Business Example As a developer, you want to create multiple instances for the local class that you have created in your ABAP Objects project. For this reason, you require the following knowledge: ●

An understanding of how to create objects



An understanding of how to handle objects

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Create objects



Handle objects

Objects as Instances of Classes

Figure 44: Overview of Instances of Classes

A class contains the generic description of an object and describes the characteristics that all objects in that class have in common. During the program runtime, you use the class to create discrete objects (instances) in the memory. This process is called instantiation. When the class is accessed for the first time, it is loaded into the memory.

58

© Copyright . All rights reserved.

Lesson: Creating and Working with Objects

Hint: Although you can use classes and static components to write complete applications, the reason for using object-oriented programming is to create and work with run time instances of classes.  Definition of Reference Variables

Figure 45: Definition of Reference Variables

To define a reference variable, use the DATA go_vehicle1 TYPE REF TO lcl_vehicle, which is typed as a pointer to objects of type lcl_vehicle. The null reference is the initial value of a reference variable.

© Copyright . All rights reserved.

59

Unit 2: Fundamental Object-Oriented Syntax

Creating Objects

Figure 46: Creating Objects

The CREATE OBJECT statement creates an object in the memory. The object attribute values are initial or assigned according to the VALUE specification. Reference Semantics of Object References

Figure 47: Reference Semantics of Object References

Object reference variables can be assigned to each other. The figure illustrates an example in which, after the MOVE statement, GO_VEHICLE1 and GO_VEHICLE2 point to the same object.

60

© Copyright . All rights reserved.

Lesson: Creating and Working with Objects

Garbage Collector

Figure 48: The Garbage Collector

Independent references are references that have not been defined within a class. The Garbage Collector is a routine that starts automatically whenever the runtime system does not have more important tasks to carry out. In this example, the reference to object (2) LCL_OBJECT is initialized. However, there is no subsequent reference point to this object. Therefore, the Garbage Collector deletes the unreferenced object. Because there is no reference point to object (4) LCL_OBJECT, it is also deleted. You can use logical query IF go_obj IS INITIAL to determine whether r_obj contains the null reference or does not point to any object.

© Copyright . All rights reserved.

61

Unit 2: Fundamental Object-Oriented Syntax

Multiple Instances

Figure 49: Reference Administration with Multiple Instantiation

To keep several objects from the same class in your program, you can define an internal table with one column that contains the object references for this class. To maintain the objects in the table, you can use statements for internal tables, such as APPEND, READ, or LOOP.

Example of Aggregation

Figure 50: Example of Aggregation

62

© Copyright . All rights reserved.

Lesson: Creating and Working with Objects

The objects in the LCL_WHEEL class have their own identity. You can create objects regardless of the existence of an object in the LCL_VEHICLE class. References are transferred to objects in class LCL_VEHICLE to create the desired association.

© Copyright . All rights reserved.

63

Unit 2: Fundamental Object-Oriented Syntax

64

© Copyright . All rights reserved.

Unit 2 Exercise 3 Create Objects

Business Example As a developer, create instances of your airplane class and ensure that the references to the objects are not lost. Template: SAPBC401_BAS_S1 Solution: SAPBC401_BAS_S2 Task 1 Define a reference variable. 1. Complete your ZBC401_##_MAIN program or copy the model solution from the previous exercise. Define a reference variable for the instances of your class LCL_AIRPLANE. 2. Define an internal table for buffering references to instances of the LCL_AIRPLANE class.

Task 2 Create airplane objects. 1. Create several instances of local class LCL_AIRPLANE and buffer their references into the internal table. Hint: Use the ABAP keyword START-OF-SELECTION to specify where the executable part of the main program begins. Otherwise, the executable statements are classified as unreachable by the syntax check. 2. Observe the execution of the program in the ABAP Debugger.

© Copyright . All rights reserved.

65

Unit 2 Solution 3 Create Objects

Business Example As a developer, create instances of your airplane class and ensure that the references to the objects are not lost. Template: SAPBC401_BAS_S1 Solution: SAPBC401_BAS_S2 Task 1 Define a reference variable. 1. Complete your ZBC401_##_MAIN program or copy the model solution from the previous exercise. Define a reference variable for the instances of your class LCL_AIRPLANE. a) See the source code extract from the model solution. 2. Define an internal table for buffering references to instances of the LCL_AIRPLANE class. a) See the source code extract from the model solution.

Task 2 Create airplane objects. 1. Create several instances of local class LCL_AIRPLANE and buffer their references into the internal table. Hint: Use the ABAP keyword START-OF-SELECTION to specify where the executable part of the main program begins. Otherwise, the executable statements are classified as unreachable by the syntax check. a) See the source code extract from the model solution. 2. Observe the execution of the program in the ABAP Debugger. a) Carry out this step in the usual manner. For more information, refer to the SAP Library.

66

© Copyright . All rights reserved.

Lesson: Creating and Working with Objects

Solution: SAPBC401_BAS_S2 REPORT sapbc401_bas_s2. TYPE-POOLS icon. *--------------------------------------------------------* * CLASS lcl_airplane DEFINITION *--------------------------------------------------------* CLASS lcl_airplane DEFINITION. * ... ENDCLASS. "lcl_airplane DEFINITION *--------------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *--------------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. * ... ENDCLASS. "lcl_airplane IMPLEMENTATION DATA: DATA:

go_airplane TYPE REF TO lcl_airplane. gt_airplanes TYPE TABLE OF REF TO lcl_airplane.

START-OF-SELECTION. CREATE OBJECT go_airplane. APPEND go_airplane TO gt_airplanes. CREATE OBJECT go_airplane. APPEND go_airplane TO gt_airplanes. CREATE OBJECT go_airplane. APPEND go_airplane TO gt_airplanes.

© Copyright . All rights reserved.

67

Unit 2: Fundamental Object-Oriented Syntax

LESSON SUMMARY You should now be able to:

68



Create objects



Handle objects

© Copyright . All rights reserved.

Unit 2 Lesson 3 Accessing Methods and Attributes

LESSON OVERVIEW This lesson explains the process of accessing methods and attributes. Business Example As a developer, you need to explain the various ways of accessing methods and attributes of a class. For this reason, you require the following knowledge: ●

An understanding of calling methods



An understanding of accessing attributes

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Call instance methods



Call static methods



Call functional methods



Access public attributes

Call Instance Methods

Figure 51: Calling Methods

© Copyright . All rights reserved.

69

Unit 2: Fundamental Object-Oriented Syntax

This section explains the use of classes and their instances, from the static connections of various instances to their practical effects. The example in the figure shows the shorter syntax for method calls supported as of SAP NetWeaver AS 6.10in which the CALL-METHOD prefix is omitted. Syntax for Calling Instance Methods

Figure 52: Calling Instance Methods – Syntax

CALL METHOD ref->method_name is the syntax used to call instance methods. When calling an instance method from within another instance method, you can omit the instance name ref. The method is automatically executed for the current object. A shorter syntax is also supported as of SAP NetWeaverAS 6.10. In this version, omit CALL METHOD and list the parameters in parentheses. There must be no space before the parentheses, but there must be at least one space after the parentheses. When you call a method that has only one import parameter, you can specify the actual parameter in the parentheses without any other additions. When you call a method that only has import parameters, you can omit the EXPORTING addition.

70

© Copyright . All rights reserved.

Lesson: Accessing Methods and Attributes

Call of Static Methods

Figure 53: Calling Static Methods – Syntax

The RECEIVING, IMPORTING, and CHANGING parameters are mutually exclusive; otherwise, the same rules apply here as they do for calling a function module. Use CALLMETHOD classname=>method_name to call static methods (also referred to as class methods). Like static attributes, static methods are addressed with their class name, since they do not need instances. As with instance methods, when you call a static method from the class, you can omit the class name; otherwise, the same rules apply here as for calling an instance method.

© Copyright . All rights reserved.

71

Unit 2: Fundamental Object-Oriented Syntax

Call of Functional Methods

Figure 54: Functional Methods

Methods that have a RETURNING parameter are described as functional methods. Functional methods cannot have an EXPORTING or a CHANGING parameter. You must also pass a value to the RETURNING parameter using the VALUE addition. You can directly call functional methods within the following expressions: Logical expressions: IF, ELSEIF, WHILE, CHECK, WAIT





Arithmetic expressions and bit expressions: COMPUTE



Case conditions: CASE, WHEN



Sources of values as a local copy: MOVE



72

Search clauses for internal tables, assuming that the operand is not a component of the table row: LOOP AT ... WHERE

© Copyright . All rights reserved.

Lesson: Accessing Methods and Attributes

Functional Methods – Examples

Figure 55: Functional Methods – Examples

In the first part of the example, the two functional instance method calls represent the two addends of an addition. The second example shows the call of a functional static method in short form. The NUMBER data object is the actual parameter for the RETURNING parameter of the method. The detailed syntax is as follows: DATA gv_number TYPE i. ... CALL METHOD lcl_vehicle=>get_n_o_vehicles RECEIVING rv_count = gv_number.

© Copyright . All rights reserved.

73

Unit 2: Fundamental Object-Oriented Syntax

Access to Public Attributes

Figure 56: Accessing Public Attributes

You can access public attributes from outside the class in the same way as method calls. You can access static attributes using classname=>static_attribute. Access instance attributes with ref->instance_attribute.

74

© Copyright . All rights reserved.

Unit 2 Exercise 4 Call Methods

Business Example As a developer, you need to fill the attributes of the objects with suitable values. You need to know how to define and call methods. Template: SAPBC401_BAS_S2 Solution: SAPBC401_BAS_S3 Task 1 Call the methods of your class. 1. Complete your ZBC401_##_MAIN program or copy the model solution from the previous exercise. Call the static method DISPLAY_N_O_AIRPLANES twice; once before and once after the instantiations. 2. Use the SET_ATTRIBUTES method to set the attributes for all objects. Choose a unique name for each airplane type (for example, 747-400). When assigning airplane types, use the information in the SAPLANE table as a guide. 3. Display the attribute values for all airplanes in a loop in the ABAP list, using the DISPLAY_ATTRIBUTES method.

Task 2 Add a functional method to your class. 1. Define the public static functional method GET_N_O_AIRPLANES in the class. The Method signature must only consist of result parameter RV_COUNT, which must be an integer. 2. Call this method in the main program and output the value in the ABAP list.

© Copyright . All rights reserved.

75

Unit 2 Solution 4 Call Methods

Business Example As a developer, you need to fill the attributes of the objects with suitable values. You need to know how to define and call methods. Template: SAPBC401_BAS_S2 Solution: SAPBC401_BAS_S3 Task 1 Call the methods of your class. 1. Complete your ZBC401_##_MAIN program or copy the model solution from the previous exercise. Call the static method DISPLAY_N_O_AIRPLANES twice; once before and once after the instantiations. a) See the source code extract from the model solution. Caution: For reasons explained in the exercise Create UML Diagrams, you may not notice any effects at the moment. 2. Use the SET_ATTRIBUTES method to set the attributes for all objects. Choose a unique name for each airplane type (for example, 747-400). When assigning airplane types, use the information in the SAPLANE table as a guide. a) See the source code extract from the model solution. 3. Display the attribute values for all airplanes in a loop in the ABAP list, using the DISPLAY_ATTRIBUTES method. a) See the source code extract from the model solution.

Task 2 Add a functional method to your class. 1. Define the public static functional method GET_N_O_AIRPLANES in the class. The Method signature must only consist of result parameter RV_COUNT, which must be an integer.

76

© Copyright . All rights reserved.

Lesson: Accessing Methods and Attributes

a) See the source code extract from the model solution. 2. Call this method in the main program and output the value in the ABAP list. a) See the source code extract from the model solution. Solution: SAPBC401_BAS_S3 Report SAPBC401_BAS_S3. TYPE-POOLS icon. *----------------------------------------------* * CLASS lcl_airplane DEFINITION *----------------------------------------------* CLASS lcl_airplane DEFINITION. PUBLIC SECTION. METHODS: set_attributes IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype, display_attributes. CLASS-METHODS: display_n_o_airplanes, get_n_o_airplanes RETURNING value(rv_count) TYPE i. PROTECTED SECTION. PRIVATE SECTION. CONSTANTS:

c_pos_1 TYPE i VALUE 30.

DATA: mv_name TYPE string, mv_planetype TYPE saplane-planetype. CLASS-DATA: gv_n_o_airplanes TYPE i. ENDCLASS. "lcl_airplane DEFINITION *----------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *----------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. METHOD

set_attributes.

mv_planetype = iv_planetype. * doesn't make sense so much, * only in order to get an effect * after calling display_n_o_airplanes: gv_n_o_airplanes = gv_n_o_airplanes + 1. ENDMETHOD. "set_attributes

© Copyright . All rights reserved.

77

Unit 2: Fundamental Object-Oriented Syntax

METHOD

display_attributes.

DATA: lv_weight TYPE saplane-weight, lv_cap TYPE saplane-tankcap. WRITE: / icon_ws_plane AS ICON, / 'Name of Airplane'(001) , AT c_pos_1 mv_name, / 'Type of Airplane:'(002), AT c_pos_1 mv_planetype. ENDMETHOD. "display_attributes METHOD display_n_o_airplanes. SKIP. WRITE: / 'Number of airplanes:'(ca1), AT c_pos_1 gv_n_o_airplanes LEFT-JUSTIFIED. ENDMETHOD. "display_n_o_airplanes METHOD get_n_o_airplanes. rv_count = gv_n_o_airplanes. ENDMETHOD. "get_n_o_airplanes ENDCLASS. "lcl_airplane IMPLEMENTATION DATA: go_airplane TYPE REF TO lcl_airplane, gt_airplanes TYPE TABLE OF REF TO lcl_airplane, gv_count TYPE i. START-OF-SELECTION. lcl_airplane=>display_n_o_airplanes( ). CREATE OBJECT go_airplane. APPEND go_airplane TO gt_airplanes. go_airplane->set_attributes( iv_name = 'LH Berlin' iv_planetype = 'A321' ). CREATE OBJECT go_airplane. APPEND go_airplane TO gt_airplanes. go_airplane->set_attributes( iv_name = 'AA New York' iv_planetype = '747-400' ). CREATE OBJECT go_airplane. APPEND go_airplane TO gt_airplanes. go_airplane->set_attributes( iv_name = 'US Hercules' iv_planetype = '747-200F' ). LOOP AT gt_airplanes INTO go_airplane. go_airplane->display_attributes( ). ENDLOOP.

78

© Copyright . All rights reserved.

Lesson: Accessing Methods and Attributes

* * * * * * * * * *

long syntax for functional call: CALL METHOD lcl_airplane=>get_n_o_airplanes RECEIVING rv_count = gv_count. a little bit shorter: lcl_airplane=>get_n_o_airplanes( RECEIVING rv_count = gv_count ). the shortest syntax for functional call:

gv_count = lcl_airplane=>get_n_o_airplanes( ). SKIP 2. WRITE: / 'Number of airplanes'(ca1), gv_count.

© Copyright . All rights reserved.

79

Unit 2: Fundamental Object-Oriented Syntax

LESSON SUMMARY You should now be able to:

80



Call instance methods



Call static methods



Call functional methods



Access public attributes

© Copyright . All rights reserved.

Unit 2 Lesson 4 Implementing Constructors in Local Classes

LESSON OVERVIEW This lesson explains the implementation of constructor methods in local classes. Business Example As a developer, you must explain the creation and use of static constructors for the class in your ABAP Objects project. For this reason, you require the following knowledge: ●

An understanding of static constructors



An understanding of how to use static constructors

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Create and use constructors

Constructor

Figure 57: (Instance) Constructor

There are two types of methods in ABAP Objects. ABAP Objects can be called implicitly or explicitly with the CALL METHOD syntax. Constructors are the first type of method.

© Copyright . All rights reserved.

81

Unit 2: Fundamental Object-Oriented Syntax

The instance constructor is a special instance method in a class and is always named CONSTRUCTOR. The constructor is automatically called at runtime with the CREATE OBJECT statement. When defining constructors, always consider the following points: No class can have more than one constructor





A constructor must be defined in the public area.



The constructor signature can only include importing parameters and exceptions.





When exceptions are raised in the constructor, no instances are created and no main memory space is occupied. Except for one unique case, you cannot call the constructor explicitly.

Note: There is no destructor in ABAP Objects; that is, there is no instance method that is automatically called from the memory immediately before the object is deleted. The corresponding comments in the SAP Library and the menu paths outside the ABAP Workbench are only contained in internal system calls. Constructor – Example

Figure 58: Constructor – Example

After the instantiation of a class, a constructor is necessary when some of the following conditions occur: ● You must allocate resources

82

© Copyright . All rights reserved.

Lesson: Implementing Constructors in Local Classes



You must initialize attributes that cannot be covered by the VALUE addition to the DATA statement



You modify static attributes



You must inform other objects about the object creation.

© Copyright . All rights reserved.

83

Unit 2: Fundamental Object-Oriented Syntax

84

© Copyright . All rights reserved.

Unit 2 Exercise 5 Create and Use Constructors

Business Example Define and implement instance constructors. Create instances of classes that contain an instance constructor. Define, raise and handle classical, non-class-based exceptions. Template: SAPBC401_BAS_S3 Solution: SAPBC401_BAS_S4 Task 1 Define an instance constructor. 1. Complete your ZBC401_##_MAIN program or copy the model solution from the previous exercise, where ## is your two-digit group number. Define a constructor with a suitable signature for the instances of your class LCL_AIRPLANE. Implement the constructor in a way that the two instance attributes are set and instance counter N_O_AIRPLANES is increased by one. 2. Remove the definition and implementation of method SET_ATTRIBUTES to ensure that an attribute of instance can be set only once during its creation.

Task 2 Create airplane objects. 1. Your CREATE OBJECT statements from the previous exercise are now syntactically incorrect. Adapt and correct them. 2. Remove calls of the SET_ATTRIBUTES method. 3. Follow the execution of the program in the ABAP Debugger. Task 3 Define additional instance attributes with technical information about the airplane. Set these attributes in your constructor by accessing database table SAPLANE. Raise an exception if the specified plane type is not found in the database. 1. In your class, define private instance attributes MV_WEIGHT (data type SAPLANE-WEIGHT) and MV_TANKCAP (data type SAPLANE_TANKCAP).

© Copyright . All rights reserved.

85

Unit 2: Fundamental Object-Oriented Syntax

2. Extend the definition of the instance constructor by adding a classical exception that is not class-based, WRONG_PLANETYPE. 3. Extend the implementation of the constructor. Read a single record from database table SAPLANE for the specified plane type and set new attributes accordingly. Raise the exception when no data is found for the given plane type. 4. Adjust the CREATE OBJECT statements so that you handle the exception. Only store the object reference in your table when the creation is successful. 5. Follow the execution of the program in the ABAP Debugger. For test purposes, specify a nonexisting airplane type to see how the exception handling works.

86

© Copyright . All rights reserved.

Unit 2 Solution 5 Create and Use Constructors

Business Example Define and implement instance constructors. Create instances of classes that contain an instance constructor. Define, raise and handle classical, non-class-based exceptions. Template: SAPBC401_BAS_S3 Solution: SAPBC401_BAS_S4 Task 1 Define an instance constructor. 1. Complete your ZBC401_##_MAIN program or copy the model solution from the previous exercise, where ## is your two-digit group number. Define a constructor with a suitable signature for the instances of your class LCL_AIRPLANE. Implement the constructor in a way that the two instance attributes are set and instance counter N_O_AIRPLANES is increased by one. a) See the source code extract from the model solution. 2. Remove the definition and implementation of method SET_ATTRIBUTES to ensure that an attribute of instance can be set only once during its creation. a) See the source code extract from the model solution.

Task 2 Create airplane objects. 1. Your CREATE OBJECT statements from the previous exercise are now syntactically incorrect. Adapt and correct them. a) See the source code extract from the model solution. 2. Remove calls of the SET_ATTRIBUTES method. a) See the source code extract from the model solution. 3. Follow the execution of the program in the ABAP Debugger. a) Carry out this step in the usual manner. For more information about the ABAP Debugger, refer to the SAP Library. Task 3

© Copyright . All rights reserved.

87

Unit 2: Fundamental Object-Oriented Syntax

Define additional instance attributes with technical information about the airplane. Set these attributes in your constructor by accessing database table SAPLANE. Raise an exception if the specified plane type is not found in the database. 1. In your class, define private instance attributes MV_WEIGHT (data type SAPLANE-WEIGHT) and MV_TANKCAP (data type SAPLANE_TANKCAP). a) See the source code extract from the model solution. 2. Extend the definition of the instance constructor by adding a classical exception that is not class-based, WRONG_PLANETYPE. a) See the source code extract from the model solution. 3. Extend the implementation of the constructor. Read a single record from database table SAPLANE for the specified plane type and set new attributes accordingly. Raise the exception when no data is found for the given plane type. a) See the source code extract from the model solution. 4. Adjust the CREATE OBJECT statements so that you handle the exception. Only store the object reference in your table when the creation is successful. a) See the source code extract from the model solution. 5. Follow the execution of the program in the ABAP Debugger. For test purposes, specify a nonexisting airplane type to see how the exception handling works. a) Carry out this step in the usual manner. For more information about the ABAP Debugger, refer to the SAP Library. Solution - SAPBC401_BAS_S4 REPORT

sapbc401_bas_s4.

TYPE-POOLS icon. *-------------------------------------------------* * CLASS lcl_airplane DEFINITION * *-------------------------------------------------* CLASS lcl_airplane DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype EXCEPTIONS wrong_planetype, display_attributes. CLASS-METHODS: display_n_o_airplanes, get_n_o_airplanes RETURNING value(rv_count) TYPE i.

88

© Copyright . All rights reserved.

Lesson: Implementing Constructors in Local Classes

PRIVATE SECTION. CONSTANTS: c_pos_1 TYPE i VALUE 30. DATA: mv_name mv_planetype mv_weight mv_tankcap

TYPE TYPE TYPE TYPE

string, saplane-planetype, saplane-weight, saplane-tankcap.

CLASS-DATA: gv_n_o_airplanes TYPE i. ENDCLASS.

"lcl_airplane DEFINITION

*--------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION * *--------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. METHOD constructor. DATA: ls_planetype TYPE saplane. mv_name = iv_name. mv_planetype = iv_planetype. SELECT SINGLE * FROM saplane INTO ls_planetype WHERE planetype = iv_planetype. IF sy-subrc 0. RAISE wrong_planetype. ELSE. mv_weight = ls_planetype-weight. mv_tankcap = ls_planetype-tankcap. gv_n_o_airplanes = gv_n_o_airplanes + 1. ENDIF. ENDMETHOD.

"constructor

METHOD display_attributes. WRITE: / icon_ws_plane AS ICON, / 'Name of Airplane'(001) , / 'Type of Airplane:'(002), / 'Weight:'(003), LEFT-JUSTIFIED, / 'Tank capacity:'(004), LEFT-JUSTIFIED. ENDMETHOD.

AT c_pos_1 mv_name, AT c_pos_1 mv_planetype, AT c_pos_1 mv_weight AT c_pos_1 mv_tankcap

"display_attributes

METHOD display_n_o_airplanes. SKIP.

© Copyright . All rights reserved.

89

Unit 2: Fundamental Object-Oriented Syntax

WRITE: / 'Number of airplanes:'(ca1), AT c_pos_1 gv_n_o_airplanes LEFT-JUSTIFIED. ENDMETHOD. "display_n_o_airplanes METHOD get_n_o_airplanes. rv_count = gv_n_o_airplanes. ENDMETHOD. "get_n_o_airplanes ENDCLASS.

"lcl_airplane IMPLEMENTATION

DATA: go_airplane TYPE REF TO lcl_airplane, gt_airplanes TYPE TABLE OF REF TO lcl_airplane, gv_count TYPE i. START-OF-SELECTION. ******************* lcl_airplane=>display_n_o_airplanes( ). CREATE OBJECT go_airplane EXPORTING iv_name = 'LH Berlin' iv_planetype = 'A321' EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. APPEND go_airplane TO gt_airplanes. ENDIF. CREATE OBJECT go_airplane EXPORTING iv_name = 'AA New York' iv_planetype = '747-400' EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. APPEND go_airplane TO gt_airplanes. ENDIF. CREATE OBJECT go_airplane EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. APPEND go_airplane TO gt_airplanes. ENDIF. LOOP AT gt_airplanes INTO go_airplane. go_airplane->display_attributes( ). ENDLOOP. gv_count = lcl_airplane=>get_n_o_airplanes( ). SKIP 2. WRITE: / 'Number of airplanes'(ca1), gv_count.

90

© Copyright . All rights reserved.

Lesson: Implementing Constructors in Local Classes

LESSON SUMMARY You should now be able to: ●

Create and use constructors

© Copyright . All rights reserved.

91

Unit 2 Lesson 5 Implementing Class Constructors in Local Classes

LESSON OVERVIEW This lesson explains the creation and use of static constructors and self-references. Business Example As a developer, you need to explain the creation and use of static constructors for the classes in your ABAP Objects project. ●

An understanding of static constructor



An understanding of self-reference

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Create and use static constructors

Static Constructor

Figure 59: Example of a Static Constructor

92

© Copyright . All rights reserved.

Lesson: Implementing Class Constructors in Local Classes

The static constructor is a special static method and is always named CLASS_CONSTRUCTOR. The static constructor is executed only once per program. The static constructor is called by the system automatically before the class is first accessed and before the first execution of the following actions: ● When an instance of the class (CREATE OBJECT) is created ●

When a static attribute of the class is accessed.



When a static method of the class is called.



When an event handler method for an event in the class is being registered.

When you define static constructors, always consider the following points: Each class does not have more than one static constructor.





The static constructor must be defined in the public area.



The constructor signature does not have importing parameters or exceptions.



The static constructor must not be called explicitly.

Self-Reference

Figure 60: Self-Reference

In some cases, you must also have a self-reference available. In ABAP Objects, self-references are always predefined, but they are only useful and syntactically available in certain contexts. You can address an object itself by using the predefined reference variable ME within its instance methods. You are not required to use theme->as a prefix in such cases, but you can use it to improve readability. However, you must use theme->prefix when distinguishing between local data objects and instance attributes with the same name.

© Copyright . All rights reserved.

93

Unit 2: Fundamental Object-Oriented Syntax

An important use of self reference is when you call a foreign method and a client object is required to export a reference to itself, you can then use ME as an actual parameter with EXPORTING or CHANGING.

94

© Copyright . All rights reserved.

Unit 2 Exercise 6 Create and Use Static Constructors

Business Example For performance reasons, you do not want to access the database each time an instance is created. Therefore, you read all the data just once in the static constructor and store it in a static attribute. Template: SAPBC401_BAS_S4 Solution: SAPBC401_BAS_S5 Task 1 Define an internal table as a private static attribute. Define a static constructor in which you fill the attribute with the complete content of database table SAPLANE. Use the ABAP Debugger to call the static constructor. 1. Complete your ZBC401_##_MAIN program or copy the model solution from the previous exercise. Define internal table GT_PLANETYPES as a private class attribute. To specify the type for the GT_PLANETYPES internal table, define private table typeTY_PLANETYPES in the class definition. Use the PLANETYPE field as a key for the internal table. 2. Define a static constructor in the LCL_AIRPLANE class. Implement the constructor in such a way that the GT_PLANETYPES internal table is filled with all rows from the SAPLANE database table. You can use the ARRAY FETCH technique for this purpose. 3. Use the ABAP Debugger to ensure that the static constructor is called correctly and that the internal table is filled in the main program. Where is the static constructor called in the main program? Task 2 Declare and implement a private static method to derive the weight and tank capacity of one plane type from the GT_PLANETYPES table. 1. Within the LCL_AIRPLANE class, define private static method GET_TECHNICAL_ATTRIBUTES.

© Copyright . All rights reserved.

95

Unit 2: Fundamental Object-Oriented Syntax

The signature must consist of one import parameter for the airplane type and two export parameters for weight and tank capacity. Use transparent table SAPLANE as a guide for specifying the types of these formal parameters. The signature must contain a classical exception which is raised when no data is found for the specified airplane type. The exception cannot be class-based. 2. Implement the method in such a way that the values for export parameters are determined by a single-record access to internal table GT_PLANETYPES. When the table does not contain any values for the airplane type, the method raises an exception. Note: The correct unit of measure must also be selected and exported. However, because of time constraints, you do not need to include it in this exercise. Task 3 Replace the database access in the instance constructor calling of method GET_TECHNICAL_ATTRIBUTES. 1. Is it possible to call the new method from the main program? Why not? 2. Call method GET_TECHNICAL_ATTRIBUTES from the constructor to obtain additional technical data. Depending on the outcome, set the corresponding private attributes or raise the exception of the constructor. 3. Observe the execution of the program in the ABAP Debugger . 4. Which alternative solutions could be used to solve the tasks?

96

© Copyright . All rights reserved.

Unit 2 Solution 6 Create and Use Static Constructors

Business Example For performance reasons, you do not want to access the database each time an instance is created. Therefore, you read all the data just once in the static constructor and store it in a static attribute. Template: SAPBC401_BAS_S4 Solution: SAPBC401_BAS_S5 Task 1 Define an internal table as a private static attribute. Define a static constructor in which you fill the attribute with the complete content of database table SAPLANE. Use the ABAP Debugger to call the static constructor. 1. Complete your ZBC401_##_MAIN program or copy the model solution from the previous exercise. Define internal table GT_PLANETYPES as a private class attribute. To specify the type for the GT_PLANETYPES internal table, define private table typeTY_PLANETYPES in the class definition. Use the PLANETYPE field as a key for the internal table. a) See the source code extract from the model solution. 2. Define a static constructor in the LCL_AIRPLANE class. Implement the constructor in such a way that the GT_PLANETYPES internal table is filled with all rows from the SAPLANE database table. You can use the ARRAY FETCH technique for this purpose. a) See the source code extract from the model solution. 3. Use the ABAP Debugger to ensure that the static constructor is called correctly and that the internal table is filled in the main program. Where is the static constructor called in the main program? a) Before the class is accessed for the first time (before DISPLAY_N_O_AIRPLANES, in this case). Task 2 Declare and implement a private static method to derive the weight and tank capacity of one plane type from the GT_PLANETYPES table.

© Copyright . All rights reserved.

97

Unit 2: Fundamental Object-Oriented Syntax

1. Within the LCL_AIRPLANE class, define private static method GET_TECHNICAL_ATTRIBUTES. The signature must consist of one import parameter for the airplane type and two export parameters for weight and tank capacity. Use transparent table SAPLANE as a guide for specifying the types of these formal parameters. The signature must contain a classical exception which is raised when no data is found for the specified airplane type. The exception cannot be class-based. a) See the source code extract from the model solution. 2. Implement the method in such a way that the values for export parameters are determined by a single-record access to internal table GT_PLANETYPES. When the table does not contain any values for the airplane type, the method raises an exception. a) See the source code extract from the model solution.

Note: The correct unit of measure must also be selected and exported. However, because of time constraints, you do not need to include it in this exercise. Task 3 Replace the database access in the instance constructor calling of method GET_TECHNICAL_ATTRIBUTES. 1. Is it possible to call the new method from the main program? Why not? a) You can only call the new method from the main program if the method is public. Because the new method in this case is a private method, it can only be called from within the LCL_AIRPLANE class. 2. Call method GET_TECHNICAL_ATTRIBUTES from the constructor to obtain additional technical data. Depending on the outcome, set the corresponding private attributes or raise the exception of the constructor. a) See the source code extract from the model solution. 3. Observe the execution of the program in the ABAP Debugger . a) Carry out this step in the usual manner. For more information on the ABAP Debugger, refer to the SAP Library. 4. Which alternative solutions could be used to solve the tasks? a) Define GET_TECHNCAL_ATTRIBUTES as instance method without the PLANETYPE import parameter. If the method is defined as an instance method, it can access the MV_PLANETYPE attribute directly (as ME->MV_PLANETYPE). In this case, the import parameter is not needed. b) Do not use a method to read GT_PLANETYPES.

98

© Copyright . All rights reserved.

Lesson: Implementing Class Constructors in Local Classes

In the instance constructor, you can access the class attribute GT_PLANETYPES directly (as ME->GT_PLANETYPES). Solution - SAPBC401_BAS_S5 REPORT

sapbc401_bas_s5.

TYPE-POOLS icon. *-------------------------------------------------* * CLASS lcl_airplane DEFINITION *-------------------------------------------------* CLASS lcl_airplane DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype EXCEPTIONS wrong_planetype, display_attributes. CLASS-METHODS: class_constructor, display_n_o_airplanes, get_n_o_airplanes RETURNING value(rv_count) TYPE i. PRIVATE SECTION. TYPES: ty_planetypes TYPE STANDARD TABLE OF saplane WITH NON-UNIQUE KEY planetype. CONSTANTS: c_pos_1 TYPE i VALUE 30. DATA: mv_name mv_planetype mv_weight mv_tankcap

TYPE TYPE TYPE TYPE

string, saplane-planetype, saplane-weight, saplane-tankcap.

CLASS-DATA: gv_n_o_airplanes TYPE i, gt_planetypes TYPE ty_planetypes. CLASS-METHODS: get_technical_attributes IMPORTING iv_type TYPE saplane-planetype EXPORTING ev_weight TYPE saplane-weight ev_tankcap TYPE saplane-tankcap

© Copyright . All rights reserved.

99

Unit 2: Fundamental Object-Oriented Syntax

EXCEPTIONS wrong_planetype. ENDCLASS.

"lcl_airplane DEFINITION

*------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. METHOD class_constructor. SELECT * FROM saplane INTO TABLE gt_planetypes. ENDMETHOD. "class_constructor *

METHOD constructor. DATA: ls_planetype TYPE saplane. mv_name = iv_name. mv_planetype = iv_planetype.

* * *

* *

SELECT SINGLE * FROM saplane INTO ls_planetype WHERE planetype = iv_planetype. get_technical_attributes( EXPORTING iv_type = iv_planetype IMPORTING ev_weight = mv_weight ev_tankcap = mv_tankcap EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ELSE. mv_weight = ls_planetype-weight. mv_tankcap = ls_planetype-tankcap. gv_n_o_airplanes = gv_n_o_airplanes + 1. ENDIF. ENDMETHOD.

"constructor

METHOD display_attributes. WRITE: / icon_ws_plane AS ICON, / 'Name of Airplane'(001) , / 'Type of Airplane:'(002), / 'Weight:'(003), LEFT-JUSTIFIED, / 'Tank capacity:'(004), LEFT-JUSTIFIED. ENDMETHOD.

AT c_pos_1 mv_name, AT c_pos_1 mv_planetype, AT c_pos_1 mv_weight AT c_pos_1 mv_tankcap

"display_attributes

METHOD display_n_o_airplanes. SKIP. WRITE: / 'Number of airplanes:'(ca1),

100

© Copyright . All rights reserved.

Lesson: Implementing Class Constructors in Local Classes

AT c_pos_1 gv_n_o_airplanes LEFT-JUSTIFIED. ENDMETHOD. "display_n_o_airplanes METHOD get_n_o_airplanes. rv_count = gv_n_o_airplanes. ENDMETHOD. "get_n_o_airplanes METHOD get_technical_attributes. DATA: ls_planetype TYPE saplane. READ TABLE gt_planetypes INTO ls_planetype WITH TABLE KEY planetype = iv_type TRANSPORTING weight tankcap. IF sy-subrc = 0. ev_weight = ls_planetype-weight. ev_tankcap = ls_planetype-tankcap. ELSE. RAISE wrong_planetype. ENDIF. ENDMETHOD. "get_technical_attributes ENDCLASS. "lcl_airplane IMPLEMENTATION DATA: go_airplane TYPE REF TO lcl_airplane, gt_airplanes TYPE TABLE OF REF TO lcl_airplane, gv_count TYPE i. START-OF-SELECTION. ******************* lcl_airplane=>display_n_o_airplanes( ). CREATE OBJECT go_airplane EXPORTING iv_name = 'LH Berlin' iv_planetype = 'A321' EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. APPEND go_airplane TO gt_airplanes. ENDIF. CREATE OBJECT go_airplane EXPORTING iv_name = 'AA New York' iv_planetype = '747-400' EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. APPEND go_airplane TO gt_airplanes. ENDIF. CREATE OBJECT go_airplane EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' EXCEPTIONS

© Copyright . All rights reserved.

101

Unit 2: Fundamental Object-Oriented Syntax

wrong_planetype = 1. IF sy-subrc = 0. APPEND go_airplane TO gt_airplanes. ENDIF. LOOP AT gt_airplanes INTO go_airplane. go_airplane->display_attributes( ). ENDLOOP. gv_count = lcl_airplane=>get_n_o_airplanes( ). SKIP 2. WRITE: / 'Number of airplanes'(ca1), gv_count.

102

© Copyright . All rights reserved.

Lesson: Implementing Class Constructors in Local Classes

LESSON SUMMARY You should now be able to: ●

Create and use static constructors

© Copyright . All rights reserved.

103

Unit 2: Fundamental Object-Oriented Syntax

104

© Copyright . All rights reserved.

Unit 2 Learning Assessment

1. The CLASS statement can be nested, that is, you cannot define a class within a class. Determine whether this statement is true or false. X

True

X

False

2. Which one of the following syntax elements define the static attributes? Choose the correct answer. X

A CLASS-DATA

X

B DATA

X

C LIKE

3. Which of the following options is used to create an object? Choose the correct answer. X

A CREATE OBJECT ref_name

X

B APPEND ref_name

X

C CLASS ref_name

4. The Garbage Collector is a system routine that starts automatically if the runtime system does not have important tasks to carry out. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

105

Unit 2: Learning Assessment

5. Independent references are references that have been defined within a class. Determine whether this statement is true or false. X

True

X

False

6. You cannot create and address the objects using reference variables. Determine whether this statement is true or false. X

True

X

False

7. During program runtime, you create discrete objects (instances) in memory for an existing class. This process is called instantiation. Determine whether this statement is true or false. X

True

X

False

8. Which of the following parameters are mutually exclusive? Choose the correct answers. X

A RECEIVING

X

B IMPORTING

X

C EXCEPTIONS

X

D CHANGING

9. When calling a static method from within the class, you can omit the class name. Determine whether this statement is true or false.

106

X

True

X

False

© Copyright . All rights reserved.

Unit 2: Learning Assessment

10. Which of the following expression(s) is used to call functional methods directly? Choose the correct answers. X

A ELSEIF

X

B COMPUTE

X

C MOVE

X

D WHILE

11. You can describe methods that have a _________ parameter as functional methods. Choose the correct answer. X

A EXPORTING

X

B CHANGING

X

C RETURNING

12. You have to pass the RETURNING parameter using the VALUE addition, that is, pass by value. Determine whether this statement is true or false. X

True

X

False

13. You can access static attributes using ____________. Choose the correct answer. X

A classname=>method_name

X

B classname=>static_attribute

X

C ref->instance_attribute

14. The _____________ is a special instance method in a class. Choose the correct answer. X

A constructor

X

B function

X

C attributes

© Copyright . All rights reserved.

107

Unit 2: Learning Assessment

15. The constructor is automatically called at runtime with the CREATE OBJECT statement. Determine whether this statement is true or false. X

True

X

False

16. Which of the following points do you consider when defining static constructors? Choose the correct answer. X

A Each class has not more than one static constructor.

X

B The static constructor must be defined in the private area.

X

C The constructor’s signature can have importing parameters or exceptions.

X

D The static constructor must be called explicitly from the class.

17. The constructor’s signature can have importing parameters or exceptions. Determine whether this statement is true or false.

108

X

True

X

False

© Copyright . All rights reserved.

Unit 2 Learning Assessment - Answers

1. The CLASS statement can be nested, that is, you cannot define a class within a class. Determine whether this statement is true or false. X

True

X

False

2. Which one of the following syntax elements define the static attributes? Choose the correct answer. X

A CLASS-DATA

X

B DATA

X

C LIKE

3. Which of the following options is used to create an object? Choose the correct answer. X

A CREATE OBJECT ref_name

X

B APPEND ref_name

X

C CLASS ref_name

4. The Garbage Collector is a system routine that starts automatically if the runtime system does not have important tasks to carry out. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

109

Unit 2: Learning Assessment - Answers

5. Independent references are references that have been defined within a class. Determine whether this statement is true or false. X

True

X

False

6. You cannot create and address the objects using reference variables. Determine whether this statement is true or false. X

True

X

False

7. During program runtime, you create discrete objects (instances) in memory for an existing class. This process is called instantiation. Determine whether this statement is true or false. X

True

X

False

8. Which of the following parameters are mutually exclusive? Choose the correct answers. X

A RECEIVING

X

B IMPORTING

X

C EXCEPTIONS

X

D CHANGING

9. When calling a static method from within the class, you can omit the class name. Determine whether this statement is true or false.

110

X

True

X

False

© Copyright . All rights reserved.

Unit 2: Learning Assessment - Answers

10. Which of the following expression(s) is used to call functional methods directly? Choose the correct answers. X

A ELSEIF

X

B COMPUTE

X

C MOVE

X

D WHILE

11. You can describe methods that have a _________ parameter as functional methods. Choose the correct answer. X

A EXPORTING

X

B CHANGING

X

C RETURNING

12. You have to pass the RETURNING parameter using the VALUE addition, that is, pass by value. Determine whether this statement is true or false. X

True

X

False

13. You can access static attributes using ____________. Choose the correct answer. X

A classname=>method_name

X

B classname=>static_attribute

X

C ref->instance_attribute

© Copyright . All rights reserved.

111

Unit 2: Learning Assessment - Answers

14. The _____________ is a special instance method in a class. Choose the correct answer. X

A constructor

X

B function

X

C attributes

15. The constructor is automatically called at runtime with the CREATE OBJECT statement. Determine whether this statement is true or false. X

True

X

False

16. Which of the following points do you consider when defining static constructors? Choose the correct answer. X

A Each class has not more than one static constructor.

X

B The static constructor must be defined in the private area.

X

C The constructor’s signature can have importing parameters or exceptions.

X

D The static constructor must be called explicitly from the class.

17. The constructor’s signature can have importing parameters or exceptions. Determine whether this statement is true or false.

112

X

True

X

False

© Copyright . All rights reserved.

UNIT 3

Inheritance and Casting

Lesson 1 Implementing Inheritance Exercise 7: Implement Inheritance

114 123

Lesson 2 Implementing Up-Casts Using Inheritance Exercise 8: Implement Up-Casts

134 137

Lesson 3 Implementing Polymorphism Using Inheritance Exercise 9: Implement Polymorphism Using Inheritance

142 147

Lesson 4 Implementing Down-Casts Using Inheritance Exercise 10: Implement Down-Casts

154 157

UNIT OBJECTIVES ●

Explain generalization and specialization



Implement inheritance



Access elements of classes in inheritance



Implement up-casts using inheritance



Explain polymorphism



Implement polymorphism using inheritance



Implement down-casts using inheritance



Model class hierarchies

© Copyright . All rights reserved.

113

Unit 3 Lesson 1 Implementing Inheritance

LESSON OVERVIEW This lesson explains the concept of inheritance, its implementation and casting. Business Example As a developer, you need to implement inheritance for the class in your ABAP objects project. For this reason, you require the following knowledge: ●

An understanding of inheritance



An understanding of Generalization and Specialization

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Explain generalization and specialization



Implement inheritance



Access elements of classes in inheritance

Generalization and Specialization

Figure 61: Example of Generalization and Specialization

114

© Copyright . All rights reserved.

Lesson: Implementing Inheritance

Specialization describes a relationship in which one class (subclass) inherits all the main characteristics of another class (superclass). The subclass can also add new components (attributes, methods, and so on) and replace the implementations in inherited methods. In the latter case, the method name in the Unified Modeling Language (UML) diagram is renamed within the subclass. Specialization is an implementation relationship that emphasizes the similarities of the classes. In the above example, the common components of classes LCL_CAR, LCL_TRUCK, and LCL_BUS are defined in the UML model in the superclass, LCL_VEHICLE. The common components of the subclasses only need to be defined and implemented in the superclass and they are inherited by all the subclasses. Specialization is described as an "is a" relationship semantically. For example, a truck is a specific vehicle. Reversing the point of view is referred to as generalization. Characteristics of Generalization and Specialization

Figure 62: Characteristics of Generalization/Specialization

Generalization and specialization provides a significantly better structure for your software because commonly used elements only need to be stored once in a central location (in the superclass). These elements are then automatically available to all subclasses. Changes made at a later stage have an immediate effect on the subclasses. Therefore, do not alter the semantics when you change a superclass. You need knowledge of the implementation of the superclass to decide whether the inherited components from the superclass are sufficient for the subclass or if they must be extended. Generalization/specialization, therefore, provides strong links between the superclass and the subclass. When you develop additional subclasses, adapt the superclasses, too. The creation of a subclass sometimes leads to additional requirements for the superclass. For example, when a subclass requires certain protected components, or, when the details of implementation of superclass are required to change because of the method implementations in subclasses. The developer of superclass cannot predict all the requirements that subclasses need from the superclass.

© Copyright . All rights reserved.

115

Unit 3: Inheritance and Casting

Implementation of Inheritance

Figure 63: Inheritance – Syntax

In ABAP Objects, an inheritance relationship is defined for a subclass using the INHERITING FROM addition, followed by the superclass directly above the subclass. Usually, Inheritance hierarchies of varying complexity can be created when a superclass inherits from another superclass; but, there is no multiple inheritance in ABAP Objects, that is, only one superclass can be specified directly above a class. However, you can use interfaces in ABAP Objects to simulate multiple inheritance. Inheritance must be used to implement generalization and specialization relationships. A superclass is a generalization of its subclasses. The subclasses are in turn different specializations of their superclasses. Thus, additions or changes are permitted in the subclasses but  you can never remove anything from a superclass in a subclass. Inheritance is a one-sided relationship. In other words, subclasses recognize their direct superclasses but superclasses do not recognize their subclasses. In this example, the subclass also contains the set_type method. The subclass also defines the get_cargo method.

116

© Copyright . All rights reserved.

Lesson: Implementing Inheritance

Redefinition of Methods

Figure 64: Redefining Methods

Redefinition is when the implementation of an inherited instance method is changed for the subclass, without changing the signature. Because the visibility section for the superclass must remain the same, therefore, redefinition is not possible within the PRIVATE SECTION. When you use the REDEFINITION addition, you will specify a new implementation part for the inherited method. Since the signature may not be changed, you do not need to define the method parameters and exceptions again. Within the redefined implementation part of the method, you can use the predefined prefix “super->...” to access components in the superclass. You may need to do this when redefining a method to call the original method of the superclass.

© Copyright . All rights reserved.

117

Unit 3: Inheritance and Casting

Preserving Semantics During Redefinition

Figure 65: Preserving Semantics During Redefinition

In this example, the two redefined methods provide completely different information. The semantics of the method remains the same.

Definition of Subclass Constructors

Figure 66: Definition of the Constructor in Subclasses

A redefinition, as described for the above methods would not be useful in the case of the constructor. In the subclass, either the constructor of the superclass can be used without any 

118

© Copyright . All rights reserved.

Lesson: Implementing Inheritance

changes  or the subclass has been expanded and the new parameters are now required in the constructors signature. In ABAP Objects, the constructor is not inherited like normal methods. Any class can define its own constructor that is fully independent from the definition of the constructor in its superclass. A subclass can even define a constructor if there is no constructor in the superclass. However, when implementing the subclass constructor, it is mandatory to refer to the constructor of the immediate superclass. By doing so, it is ensured that the constructor of class is always executed, whether the created object is an instance of the class itself, or an instance of one of its subclasses. Because of this enforced reference of the superclass constructor, the subclass constructor adds parameters to the signature of the superclass constructor rather than completely changing it.

Hint: In this context, the concept of overloading is of relevance. With overloading, a method can have several definitions with different signatures and different implementations. The concept of overloading is not supported in ABAP Objects. The usual work-around is one signature with different sets of optional parameters. In contrast to instance constructors, the static constructor automatically ensures that the static constructors of all its superclasses have already been executed before the static constructor in a particular class is executed in the runtime system. Rules for Calling the Constructor

Figure 67: Rules for Calling the Constructor

If a subclass has not changed its instance constructor, the constructor is adopted from the superclass. The implementation is also inherited from the superclass.

© Copyright . All rights reserved.

119

Unit 3: Inheritance and Casting

Inheritance and Visibility

Figure 68: Inheritance and Visibility

Inheritance provides an extension of the visibility concept through protected components (PROTECTED SECTION). The visibility of protected components lies between public and private components. Protected components are visible to all subclasses and the class itself. When defining local classes in ABAP Objects, follow the syntactical sequence of the PUBLIC SECTION, the PROTECTED SECTION, and the PRIVATE SECTION.

120

© Copyright . All rights reserved.

Lesson: Implementing Inheritance

Visibility Section – Protected Versus Private

Figure 69: Protected Versus Private Section

The components inherited from the superclass  may not be visible  in the subclass. A subclass can receive private components from its superclass which cannot  be addressd in the syntax of the subclass. Private components of superclasses can only be addressed indirectly using public or protected methods from the superclass, which in turn, can access the private attributes. These restrictions are necessary to ensure that centralized maintenance is possible. In this example, it is possible to access the protected constant C_POS_1 in superclass LCL_VEHICLE directly from its subclass LCL_BUS. On the other hand, the only way to access the private MV_MAKE and MV_MODEL attributes from the subclasses of LCL_VEHICLE is to call methods of LCL_VEHICLE. These methods have to be public or protected. Using the PRIVATE SECTION, you can change superclasses without the need to know the subclasses. As long as the changes you make do not affect the semantics, you do not need to adapt the subclasses. This is because they only indirectly access the private components from the superclass.

Inheritance and Static Components Summary of static components and inheritance are as follows:  ●







A class that defines a public or protected static attribute shares this attribute with all its subclasses. Static methods cannot be redefined. The static constructor of a superclass is executed when the superclass or one of its subclasses is accessed for the first time. A subclass can always have a static constructor irrespective of the superclass.

© Copyright . All rights reserved.

121

Unit 3: Inheritance and Casting



122

If a subclass and its superclass both have a static constructor then both constructors are executed when we access the subclass for the first time. In this case, first access to the subclass is also the first access to the superclass.

© Copyright . All rights reserved.

Unit 3 Exercise 7 Implement Inheritance

Business Example You must refine your airplane management program. Create classes for specific airplanes in relation to a general airplane class. Template SAPBC401_BAS_S5 Solution SAPBC401_INH_S1 Task 1 Define the local class LCL_PASSENGER_PLANE for passenger planes. Define the class as a subclass of LCL_AIRPLANE. Add specific attributes and methods and redefine the DISPLAY_ATTRIBUTES method. 1.  Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the template program. Define a new local class LCL_PASSENGER_PLANE and make it a subclass of the already existing LCL_AIRPLANE. 2. Is there a specific sequence in which you have to define the classes in the source code?

3. The class must have a private instance attribute, MV_SEATS, with the same type as the table field SFLIGHT-SEATSMAX. 4. Define and implement an instance constructor that assigns values to all instance attributes in the class. 5. Redefine method DISPLAY_ATTRIBUTES so that all instance attributes are displayed using the WRITE statement. Make sure the output of specific attributes are aligned with the output from the superclass. Therefore, change the visibility of the C_POS_1 constant so that you can use it in your subclass.

Task 2 In the class LCL_AIRPLANE, define the local subclass LCL_CARGO_PLANE for cargo planes.

© Copyright . All rights reserved.

123

Unit 3: Inheritance and Casting

1. The class must have a private instance attribute, MV_CARGO, with the same type as the table field SCPLANE-CARGOMAX. 2. Define and implement an instance constructor that assigns values to all instance attributes in the class. 3. Redefine DISPLAY_ATTRIBUTES so that all instance attributes are displayed using the WRITE statement.

Task 3 Create instances of your new classes and display their attributes. 1. In the main program, define a suitably typed reference variable for each of your new classes. 2. Before instantiating any objects, call the static method DISPLAY_N_O_AIRPLANES. 3. Use the two references to create an instance of each of the subclasses LCL_PASSENGER_PLANE and LCL_CARGO_PLANE. Decide for yourself how to fill the attributes. 4. Call the DISPLAY_ATTRIBUTES method for both instances. 5. Call the static method DISPLAY_ATTRIBUTES second time.

Task 4 Debug your program. 1. Could the method GET_TECHNICAL_ATTRIBUTES be called directly from the redefined method DISPLAY_ATTRIBUTES of the subclasses?

2. Observe the program flow in the ABAP Debugger, paying special attention to the call of the DISPLAY_ATTRIBUTES method.

124

© Copyright . All rights reserved.

Unit 3 Solution 7 Implement Inheritance

Business Example You must refine your airplane management program. Create classes for specific airplanes in relation to a general airplane class. Template SAPBC401_BAS_S5 Solution SAPBC401_INH_S1 Task 1 Define the local class LCL_PASSENGER_PLANE for passenger planes. Define the class as a subclass of LCL_AIRPLANE. Add specific attributes and methods and redefine the DISPLAY_ATTRIBUTES method. 1.  Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the template program. Define a new local class LCL_PASSENGER_PLANE and make it a subclass of the already existing LCL_AIRPLANE. a)  See the source code extract from the model solution. 2. Is there a specific sequence in which you have to define the classes in the source code? A superclass has to be defined first. Otherwise, the syntax check will not know it when you refer to superclass in the INHERITING FROM part of the subclass definition. 3. The class must have a private instance attribute, MV_SEATS, with the same type as the table field SFLIGHT-SEATSMAX. a) See the source code extract from the model solution. 4. Define and implement an instance constructor that assigns values to all instance attributes in the class. a) See the source code extract from the model solution. 5. Redefine method DISPLAY_ATTRIBUTES so that all instance attributes are displayed using the WRITE statement. Make sure the output of specific attributes are aligned with the output from the superclass. Therefore, change the visibility of the C_POS_1 constant so that you can use it in your subclass.

© Copyright . All rights reserved.

125

Unit 3: Inheritance and Casting

a) See the source code extract from the model solution.

Task 2 In the class LCL_AIRPLANE, define the local subclass LCL_CARGO_PLANE for cargo planes. 1. The class must have a private instance attribute, MV_CARGO, with the same type as the table field SCPLANE-CARGOMAX. a) See the source code extract from the model solution. 2. Define and implement an instance constructor that assigns values to all instance attributes in the class. a) See the source code extract from the model solution. 3. Redefine DISPLAY_ATTRIBUTES so that all instance attributes are displayed using the WRITE statement. a) See the source code extract from the model solution.

Task 3 Create instances of your new classes and display their attributes. 1. In the main program, define a suitably typed reference variable for each of your new classes. a) See the source code extract from the model solution. 2. Before instantiating any objects, call the static method DISPLAY_N_O_AIRPLANES. a) See the source code extract from the model solution. 3. Use the two references to create an instance of each of the subclasses LCL_PASSENGER_PLANE and LCL_CARGO_PLANE. Decide for yourself how to fill the attributes. a) See the source code extract from the model solution. 4. Call the DISPLAY_ATTRIBUTES method for both instances. a) See the source code extract from the model solution. 5. Call the static method DISPLAY_ATTRIBUTES second time. a) See the source code extract from the model solution.

Task 4 Debug your program.

126

© Copyright . All rights reserved.

Lesson: Implementing Inheritance

1. Could the method GET_TECHNICAL_ATTRIBUTES be called directly from the redefined method DISPLAY_ATTRIBUTES of the subclasses? No, because the method is private in the superclass.

2. Observe the program flow in the ABAP Debugger, paying special attention to the call of the DISPLAY_ATTRIBUTES method. a) Carry out this step in the usual manner. Solution - SAPBC401_INH_S1 REPORT

sapbc401_inh_s1.

TYPE-POOLS icon. *------------------------------------------------* * CLASS lcl_airplane DEFINITION *------------------------------------------------* CLASS lcl_airplane DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype EXCEPTIONS wrong_planetype, display_attributes. CLASS-METHODS: class_constructor, display_n_o_airplanes, get_n_o_airplanes RETURNING value(rv_count) TYPE i. PROTECTED SECTION. CONSTANTS: c_pos_1 TYPE i VALUE 30. PRIVATE SECTION. TYPES: ty_planetypes TYPE STANDARD TABLE OF saplane WITH NON-UNIQUE KEY planetype. DATA: mv_name mv_planetype mv_weight mv_tankcap

TYPE TYPE TYPE TYPE

string, saplane-planetype, saplane-weight, saplane-tankcap.

CLASS-DATA:

© Copyright . All rights reserved.

127

Unit 3: Inheritance and Casting

gv_n_o_airplanes TYPE i, gt_planetypes TYPE ty_planetypes. CLASS-METHODS: get_technical_attributes IMPORTING iv_type TYPE saplane-planetype EXPORTING ev_weight TYPE saplane-weight ev_tankcap TYPE saplane-tankcap EXCEPTIONS wrong_planetype. ENDCLASS.

"lcl_airplane DEFINITION

*-------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *-------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. METHOD class_constructor. SELECT * FROM saplane INTO TABLE gt_planetypes. ENDMETHOD. "class_constructor METHOD constructor. mv_name = iv_name. mv_planetype = iv_planetype. get_technical_attributes( EXPORTING iv_type = iv_planetype IMPORTING ev_weight = mv_weight ev_tankcap = mv_tankcap EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ELSE. gv_n_o_airplanes = gv_n_o_airplanes + 1. ENDIF. ENDMETHOD.

"constructor

METHOD display_attributes. WRITE: / icon_ws_plane AS ICON, / 'Name of Airplane'(001) , / 'Type of Airplane:'(002), / 'Weight:'(003), LEFT-JUSTIFIED, / 'Tank capacity:'(004), LEFT-JUSTIFIED. ENDMETHOD.

128

AT c_pos_1 mv_name, AT c_pos_1 mv_planetype, AT c_pos_1 mv_weight AT c_pos_1 mv_tankcap

"display_attributes

© Copyright . All rights reserved.

Lesson: Implementing Inheritance

METHOD display_n_o_airplanes. SKIP. WRITE: / 'Number of airplanes:'(ca1), AT c_pos_1 gv_n_o_airplanes LEFT-JUSTIFIED. ENDMETHOD. "display_n_o_airplanes METHOD get_n_o_airplanes. rv_count = gv_n_o_airplanes. ENDMETHOD. "get_n_o_airplanes METHOD get_technical_attributes. DATA: ls_planetype TYPE saplane. READ TABLE gt_planetypes INTO ls_planetype WITH TABLE KEY planetype = iv_type TRANSPORTING weight tankcap. IF sy-subrc = 0. ev_weight = ls_planetype-weight. ev_tankcap = ls_planetype-tankcap. ELSE. RAISE wrong_planetype. ENDIF. ENDMETHOD. "get_technical_attributes ENDCLASS.

"lcl_airplane IMPLEMENTATION

*------------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *------------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype iv_cargo TYPE s_plan_car EXCEPTIONS wrong_planetype, display_attributes REDEFINITION. PRIVATE SECTION. DATA: mv_cargo TYPE s_plan_car. ENDCLASS.

"lcl_cargo_plane DEFINITION

*------------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *------------------------------------------------*

© Copyright . All rights reserved.

129

Unit 3: Inheritance and Casting

CLASS lcl_cargo_plane IMPLEMENTATION. METHOD constructor. super->constructor( EXPORTING iv_name = iv_name iv_planetype = iv_planetype EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ENDIF. mv_cargo = iv_cargo. ENDMETHOD. "constructor METHOD display_attributes. super->display_attributes( ). WRITE: / 'Max Cargo:'(005), AT c_pos_1 mv_cargo LEFT-JUSTIFIED. ULINE. ENDMETHOD. "display_attributes ENDCLASS.

"lcl_cargo_plane IMPLEMENTATION

*------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype iv_seats TYPE s_seatsmax EXCEPTIONS wrong_planetype, display_attributes REDEFINITION. PRIVATE SECTION. DATA: mv_seats TYPE s_seatsmax. ENDCLASS.

"lcl_passenger_plane DEFINITION

*------------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *------------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. METHOD constructor. super->constructor(

130

© Copyright . All rights reserved.

Lesson: Implementing Inheritance

EXPORTING iv_name = iv_name iv_planetype = iv_planetype EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ENDIF. mv_seats = iv_seats. ENDMETHOD. "constructor METHOD display_attributes. super->display_attributes( ). WRITE: / 'Max Seats:'(006), AT c_pos_1 mv_seats LEFT-JUSTIFIED. ULINE. ENDMETHOD. "display_attributes ENDCLASS. "lcl_passenger_plane IMPLEMENTATION DATA: go_airplane go_cargo go_passenger gt_airplanes gv_count

TYPE TYPE TYPE TYPE TYPE

REF TO lcl_airplane, REF TO lcl_cargo_plane, REF TO lcl_passenger_plane, TABLE OF REF TO lcl_airplane, i.

START-OF-SELECTION. ******************* lcl_airplane=>display_n_o_airplanes( ). CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. * do nothing for now ENDIF. CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. * do nothing just now ENDIF. go_passenger->display_attributes( ).

© Copyright . All rights reserved.

131

Unit 3: Inheritance and Casting

go_cargo->display_attributes( ). gv_count = lcl_airplane=>get_n_o_airplanes( ). SKIP 2. WRITE: / 'Number of airplanes'(ca1), gv_count.

132

© Copyright . All rights reserved.

Lesson: Implementing Inheritance

LESSON SUMMARY You should now be able to: ●

Explain generalization and specialization



Implement inheritance



Access elements of classes in inheritance

© Copyright . All rights reserved.

133

Unit 3 Lesson 2 Implementing Up-Casts Using Inheritance

LESSON OVERVIEW This lesson explains the concept of up-casts and the dynamic and the static type of reference variable. This lesson also explains the method of implementing up-casts. Business Example As a developer, you need to implement the upcast concept for your ABAP object classes. For this reason, you require the following knowledge: ●

 An understanding of inheritance



 An understanding of up-casts

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Implement up-casts using inheritance

The Up-Cast

Figure 70: Up-Cast (Widening Cast) with Object References

If you assign a subclass reference to a superclass reference, this subclass ensures that all components that you can access syntactically after the cast assignment are actually available in

134

© Copyright . All rights reserved.

Lesson: Implementing Up-Casts Using Inheritance

the instance. The subclass always contains at least the same components as the superclass always the name and the signature of redefined methods are identical. The user can address only those methods and attributes from the subclass instance that they can from the superclass instance.

Hint: Note that with redefined methods, the implementation of the subclass is executed using the superclass static type of reference. In this example, after the assignment, you can only access the methods GET_MAKE, GET_COUNT, DISPLAY_ATTRIBUTES, SET_ATTRIBUTES, and ESTIMATE_FUEL of the instance LCL_TRUCK by using the reference GO_VEHICLE. If there are any restrictions regarding visibility, they are left unchanged. It is not possible to access the specific components from the class LCL_TRUCK of the instance GET_CARGO in the example using the reference GO_VEHICLE. The view or possible access to methods is either narrowed or left unchanged. There is a switch from a view of several components to a view of a few components. As the target variable can accept more dynamic types in comparison to the source variable, this assignment is also called widening cast.

Static and Dynamic Type

Figure 71: Static and Dynamic Types of References

Types of a reference variable at runtime in object oriented programming: Static





Dynamic

In the example, LCL_VEHICLE is the static type of the variable GO_VEHICLE. Depending on the cast assignment, the dynamic type is either LCL_BUS or LCL_TRUCK. In the ABAP Debugger, the dynamic type is specified in the following form:

© Copyright . All rights reserved.

135

Unit 3: Inheritance and Casting

object_id

Note: Assignments between reference variables are possible whenever the static type of the target variables is more general or equal to the dynamic type of the source variables.

136

© Copyright . All rights reserved.

Unit 3 Exercise 8 Implement Up-Casts

Business Example As a developer, your airplane management program should display the attributes of the airplane objects generically, that is, it should be open to future extensions with additional airplane classes. Template SAPBC401_INH_S1 Solution SAPBC401_INH_S2 Task 1 Buffer the airplane references in a suitable type of internal table. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the sample solution program from the previous exercise. 2. In your main program, define an internal table for buffering airplane references if you do not already have one. The row type of the internal table should be REF TO LCL_AIRPLANE.

Task 2 Display the attributes of all airplane types that were created so far. 1. Insert the references to your passenger and cargo airplanes into the internal table. 2. Program a loop through the contents of the internal table. Call the DISPLAY_ATTRIBUTES method every time the loop runs.

Task 3  Analyze your program. 1.  What would happen if the method DISPLAY_ATTRIBUTES had not been redefined in the subclasses?

2. Follow the program flow in the ABAP Debugger, paying special attention to the call of the method DISPLAY_ATTRIBUTES.

© Copyright . All rights reserved.

137

Unit 3 Solution 8 Implement Up-Casts

Business Example As a developer, your airplane management program should display the attributes of the airplane objects generically, that is, it should be open to future extensions with additional airplane classes. Template SAPBC401_INH_S1 Solution SAPBC401_INH_S2 Task 1 Buffer the airplane references in a suitable type of internal table. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the sample solution program from the previous exercise. a)  Carry out this step as usual. Additional information is available in the SAP Library. 2. In your main program, define an internal table for buffering airplane references if you do not already have one. The row type of the internal table should be REF TO LCL_AIRPLANE. a) See the source code extract from the model solution.

Task 2 Display the attributes of all airplane types that were created so far. 1. Insert the references to your passenger and cargo airplanes into the internal table. a) See the source code extract from the model solution. 2. Program a loop through the contents of the internal table. Call the DISPLAY_ATTRIBUTES method every time the loop runs. a) See the source code extract from the model solution.

Task 3  Analyze your program.

138

© Copyright . All rights reserved.

Lesson: Implementing Up-Casts Using Inheritance

1.  What would happen if the method DISPLAY_ATTRIBUTES had not been redefined in the subclasses?  The implementation from the superclass would be executed. Your program would not contain polymorphism. 2. Follow the program flow in the ABAP Debugger, paying special attention to the call of the method DISPLAY_ATTRIBUTES. a)  Carry out this step as usual. Additional information is available in the SAP Library. SAPBC401_INH_S2 REPORT sapbc401_inh_s2. TYPE-POOLS icon. *-----------------------------------------------* * CLASS lcl_airplane DEFINITION *-----------------------------------------------* CLASS lcl_airplane DEFINITION. ... ENDCLASS. "lcl_airplane DEFINITION *-----------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *-----------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. ... ENDCLASS. "lcl_airplane IMPLEMENTATION *-----------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *-----------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS. "lcl_cargo_plane DEFINITION *-----------------------------------------------* *CLASS lcl_cargo_plane IMPLEMENTATION *-----------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. ... ENDCLASS. "lcl_cargo_plane IMPLEMENTATION *-----------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *-----------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS. "lcl_passenger_plane DEFINITION *-----------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *-----------------------------------------------*

© Copyright . All rights reserved.

139

Unit 3: Inheritance and Casting

CLASS lcl_passenger_plane IMPLEMENTATION. ... ENDCLASS. "lcl_passenger_plane IMPLEMENTATION DATA: go_airplane TYPE REF TO lcl_airplane, go_cargo TYPE REF TO lcl_cargo_plane, go_passenger TYPE REF TO lcl_passenger_plane, gt_airplanes TYPE TABLE OF REF TO lcl_airplane, gv_count TYPE i.

START-OF-SELECTION. ******************* lcl_airplane=>display_n_o_airplanes( ). CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. APPEND go_passenger TO gt_airplanes. ENDIF. CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. APPEND go_cargo TO gt_airplanes. ENDIF. LOOP AT gt_airplanes INTO go_airplane. go_airplane->display_attributes( ). ENDLOOP. gv_count = lcl_airplane=>get_n_o_airplanes( ). SKIP 2. WRITE: / 'Number of airplanes'(ca1), gv_count.

140

© Copyright . All rights reserved.

Lesson: Implementing Up-Casts Using Inheritance

LESSON SUMMARY You should now be able to: ●

Implement up-casts using inheritance

© Copyright . All rights reserved.

141

Unit 3 Lesson 3 Implementing Polymorphism Using Inheritance

LESSON OVERVIEW This lesson explains polymorphism and implementing polymorphism using inheritance. Business Example As a developer, you need to implement polymorphism using inheritance. For this reason, you require the following knowledge: ●

An understanding of polymorphism



An understanding of generic access and upcast assignments

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Explain polymorphism



Implement polymorphism using inheritance

Generic Access

Figure 72: Generic Access After Up-Cast Assignments

A typical use for up-cast assignments is to prepare for generic access. A user who is not interested in the finer points of the instances of the subclasses but simply needs to address the shared components can use a superclass reference for this access.

142

© Copyright . All rights reserved.

Lesson: Implementing Polymorphism Using Inheritance

In the example, a travel agency LCL_RENTAL needs to manage all imaginable kinds of vehicles in one list. To manage all these vehicles in one list, ayou need to create an internal table and assign it with an appropriate type for the references to the vehicle instances. The car rental company also needs to be able to calculate the required amount of fuel for all its vehicles. In this case, the DISPLAY_ATTRIBUTES method which is defined in the superclass LCL_VEHICLE must be redefined in all subclasses. Row Type of the Internal Table in the Application – Example

Figure 73: Row Type of the Internal Table in the Application – Example

When objects of different classes (LCL_BUS, LCL_TRUCK and LCL_CAR) are specified as type superclass references (LCL_VEHICLE), these objects can be stored in an internal table. The shared components of the subclass objects can then be accessed uniformly. For this example, you need the method ADD_VEHICLE to copy the references to the vehicle types into the internal table. The import parameter of this method is already typed as the reference to the superclass.

© Copyright . All rights reserved.

143

Unit 3: Inheritance and Casting

Up-Cast and Generic Access in the Application – Example

Figure 74: Up-Cast and Generic Access in the Application – Example

In this example, the up-cast assignment occurs when the vehicle reference is transferred to the formal parameter of ADD_VEHICLE method. The shared component is generically accessed within the loop around the internal table containing all of the vehicle references. The DISPLAY_ATTRIBUTES method was inherited from the LCL_VEHICLE superclass and may have been redefined.

Polymorphism

Figure 75: Polymorphism – Generic Access Using the Superclass Reference

144

© Copyright . All rights reserved.

Lesson: Implementing Polymorphism Using Inheritance

The implementation to be executed when DISPLAY_ATTRIBUTES is called will depend on which object the superclass reference LO_VEHICLE refers to. The dynamic type (not the static type) of the reference variable is used to search for the implementation of a method. Therefore, when lo_vehicle->display_attributes is called, the implementation is not executed from LCL_VEHICLE (static type of LO_VEHICLE) because the method was redefined in all vehicle classes. When an instance receives a message to execute a particular method, the method that implemented the class of this instance is executed. If the class has not been redefined in the method, the implementation from the superclass is executed. Characteristics of Polymorphism When objects from different classes react differently to the same method calls, this is known as polymorphism. The possibility of polymorphism is one of the main strengths of inheritance. A client can handle different classes uniformly, irrespective of their implementation. The runtime system searches for the right implementation of a method on behalf of the client. Polymorphism can be used to write programs that are highly generic, that is, they do not need to be changed significantly if use cases are added. For instance, polymorphism may make it very easy to add motorbikes to this example. You simply need to define a new subclass of LCL_VEHICLE, which you can call LCL_MOTORBIKE. You would also have to redefine the inherited method DISPLAY_ATTRIBUTES. Without needing any more changes, your vehicle management system can then work with motorbikes, as well as, calculate the required fuel levels for them.

Generic Calls in the Procedural Programming Model

Figure 76: Generic Calls in the Procedural Programming Model

Using dynamic function module calls, you can program generically in ABAP, even without an object-oriented programming model. When you compare dynamic function module call with polymorphism through inheritance, the source code is less self-explanatory and is more susceptible to errors in dynamic function module call. For example, the syntax check can only

© Copyright . All rights reserved.

145

Unit 3: Inheritance and Casting

check whether the function model is called correctly or not. The syntax check cannot check whether the internal table contains a valid function module name for each vehicle or not.

146

© Copyright . All rights reserved.

Unit 3 Exercise 9 Implement Polymorphism Using Inheritance

Business Example You need to encapsulate the management of airplane instances in a new class instead of the main program. Template SAPBC401_INH_T3 Solution SAPBC401_INH_S3 Task 1 Define a local class for airlines. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the template program. If you copy the template program then you can go directly to the next step. Otherwise, copy the local class LCL_CARRIER along with the definition and implementation of the class from the template program and paste it into your own program. 2. Define a private instance attribute MT_AIRPLANES to store references to airplanes. 3. Define and implement a public method ADD_AIRPLANE so that airplane references can be added to the previously defined list MT_AIRPLANES. The method should have one import parameter that is IO_PLANE. 4. Define and implement a private instance method DISPLAY_AIRPLANES. In this method, loop at the list of airplanes and call method DISPLAY_ATTRIBUTES for each airplane. 5. Extend the implementation of the method DISPLAY_ATTRIBUTES in a way that  not only  the information about the carrie itself is displayed but also  all its airplanes. Use the previously defined DISPLAY_AIRPLANES_METHOD.

Task 2 In the main program, create an airline instance. Transfer some airplane references to the airline instance and display the attributes. 1. Remove all the statements from the main program that define the global internal table for airplane references and their insertions. 2. In the main program, define a suitably typed reference variable for your new airline class.

© Copyright . All rights reserved.

147

Unit 3: Inheritance and Casting

3. Using the reference, generate an instance of your class LCL_CARRIER. Decide for yourself how to fill the attributes. 4. Call the method ADD_AIRPLANE to transfer each airplane instance to the carrier. You may also create and transfer additional airplanes. 5. Display the attributes of the airline by calling its method DISPLAY_ATTRIBUTES.

148

© Copyright . All rights reserved.

Unit 3 Solution 9 Implement Polymorphism Using Inheritance

Business Example You need to encapsulate the management of airplane instances in a new class instead of the main program. Template SAPBC401_INH_T3 Solution SAPBC401_INH_S3 Task 1 Define a local class for airlines. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the template program. If you copy the template program then you can go directly to the next step. Otherwise, copy the local class LCL_CARRIER along with the definition and implementation of the class from the template program and paste it into your own program. a) Carry out this step in the usual manner. Additional information is available in the SAP Library. b) Refer the source code extract from the model solution. 2. Define a private instance attribute MT_AIRPLANES to store references to airplanes. a) Refer the source code extract from the model solution. 3. Define and implement a public method ADD_AIRPLANE so that airplane references can be added to the previously defined list MT_AIRPLANES. The method should have one import parameter that is IO_PLANE. a) Refer the source code extract from the model solution. 4. Define and implement a private instance method DISPLAY_AIRPLANES. In this method, loop at the list of airplanes and call method DISPLAY_ATTRIBUTES for each airplane. a) Refer the source code extract from the model solution. 5. Extend the implementation of the method DISPLAY_ATTRIBUTES in a way that  not only  the information about the carrie itself is displayed but also  all its airplanes. Use the previously defined DISPLAY_AIRPLANES_METHOD. a) Refer the source code extract from the model solution.

Task 2

© Copyright . All rights reserved.

149

Unit 3: Inheritance and Casting

In the main program, create an airline instance. Transfer some airplane references to the airline instance and display the attributes. 1. Remove all the statements from the main program that define the global internal table for airplane references and their insertions. a) Refer the source code extract from the model solution. 2. In the main program, define a suitably typed reference variable for your new airline class. a) Refer the source code extract from the model solution. 3. Using the reference, generate an instance of your class LCL_CARRIER. Decide for yourself how to fill the attributes. a) Refer the source code extract from the model solution. 4. Call the method ADD_AIRPLANE to transfer each airplane instance to the carrier. You may also create and transfer additional airplanes. a) Refer the source code extract from the model solution. 5. Display the attributes of the airline by calling its method DISPLAY_ATTRIBUTES. a) Refer the source code extract from the model solution. SAPBC401_INH_S3 REPORT sapbc401_inh_s3. TYPE-POOLS icon. *------------------------------------------------* * CLASS lcl_airplane DEFINITION *------------------------------------------------* CLASS lcl_airplane DEFINITION. ... ENDCLASS. "lcl_airplane DEFINITION *------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. ... ENDCLASS. "lcl_airplane IMPLEMENTATION *------------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *------------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS. "lcl_cargo_plane DEFINITION *------------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *------------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. ... ENDCLASS. "lcl_cargo_plane IMPLEMENTATION

150

© Copyright . All rights reserved.

Lesson: Implementing Polymorphism Using Inheritance

*------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS. "lcl_passenger_plane DEFINITION *------------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *------------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. ... ENDCLASS. "lcl_passenger_plane IMPLEMENTATION *------------------------------------------------* * CLASS lcl_carrier DEFINITION *------------------------------------------------* CLASS lcl_carrier DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string, display_attributes, add_airplane IMPORTING io_plane TYPE REF TO lcl_airplane. PRIVATE SECTION. DATA: mv_name TYPE string, mt_airplanes TYPE TABLE OF REF TO lcl_airplane. METHODS: display_airplanes. ENDCLASS. "lcl_carrier DEFINITION *------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. METHOD constructor. mv_name = iv_name. ENDMETHOD. "constructor METHOD display_attributes. SKIP 2. WRITE: icon_flight AS ICON, mv_name. ULINE. ULINE. me->display_airplanes( ). ENDMETHOD. "display_attributes METHOD add_airplane. APPEND io_plane TO mt_airplanes. ENDMETHOD. "add_airplane METHOD display_airplanes. DATA: lo_plane TYPE REF TO lcl_airplane.

© Copyright . All rights reserved.

151

Unit 3: Inheritance and Casting

LOOP AT mt_airplanes INTO lo_plane. lo_plane->display_attributes( ). ENDLOOP. ENDMETHOD. "display_airplanes ENDCLASS. "lcl_carrier IMPLEMENTATION DATA: go_carrier TYPE REF TO lcl_carrier, go_airplane TYPE REF TO lcl_airplane, go_cargo TYPE REF TO lcl_cargo_plane, go_passenger TYPE REF TO lcl_passenger_plane, gv_count TYPE i. START-OF-SELECTION. ******************* ***** Create Carrier CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly-Travel'. ***** Passenger Plane CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. go_carrier->add_airplane( go_passenger ). ENDIF. ***** cargo Plane CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. go_carrier->add_airplane( go_cargo ). ENDIF. ***** output carrier (including list of airplanes) go_carrier->display_attributes( ).

152

© Copyright . All rights reserved.

Lesson: Implementing Polymorphism Using Inheritance

LESSON SUMMARY You should now be able to: ●

Explain polymorphism



Implement polymorphism using inheritance

© Copyright . All rights reserved.

153

Unit 3 Lesson 4 Implementing Down-Casts Using Inheritance

LESSON OVERVIEW This lesson explains the concept of down-cast assignments (narrowing cast). Business Example As a developer, you need to create a subclass from the airplane class and then use casting to access different attributes. For this reason, you require the following knowledge: ●

An understanding of down-casts



An understanding of inheritance



An understanding of implementing down-casts using Inheritance

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Implement down-casts using inheritance



Model class hierarchies

The Down-Cast

Figure 77: Down-Cast  (Narrowing-Cast) with Object References

154

© Copyright . All rights reserved.

Lesson: Implementing Down-Casts Using Inheritance

Reference variables of the superclass can also refer to the subclass instances at runtime. You may copy this reference back to a reference variable of the subclass type. To assign a superclass reference to a subclass reference, you must use the down-cast assignment operator MOVE ... ?TO ... or its short form ?=. Otherwise, you get a message stating that it is not certain that all the components that can be accessed syntactically after the cast assignment are actually available in the instance. As a rule, the subclass class contains more components than the superclass. After assigning this type of reference back to a subclass reference to the implementing class, clients are no longer limited to inherited components. In the example given here, all the components of the LCL_TRUCK instance can be accessed again after the assignment using the GO_TRUCK2 reference. Therefore, usually the view is either widened or not changed. This type of assignment of reference variables is known as down-cast. There is a switch from a view of a few components to a view of many components. As the target variable can accept less dynamic types after the assignment, this assignment is also called narrowing cast. Specific Access After Down-Cast Assignments

Figure 78: Specific Access After Down-Cast Assignments

Down-cast assignments is used when you need to address specific components of instances and keep the references of these components in variables that are typed on the superclass. A user who is interested in the finer points of the instances of a subclass cannot use the superclass reference for this access because it allows access only to the shared components.

© Copyright . All rights reserved.

155

Unit 3: Inheritance and Casting

Exceptions Handling for Down-Casts

Figure 79: Down-Cast and Exception Handling in the Application - Example

In this example, a car rental company (LCL_RENTAL) has to determine the maximum capacity of its trucks, but it stores all types of vehicle references in an internal table LCL_VEHICLE. There may be a problem if there is no truck reference in the LO_VEHICLE superclass reference at runtime but the down-cast assignment operator tries to copy the reference to the now invalid reference LO_TRUCK. In contrast to the up-cast assignment, it is possible that the static type of the target variable (LO_TRUCK) is no more general than nor is the same as the dynamic type of the source variable (LO_VEHICLE), namely when LO_VEHICLE contains bus or sports car references. That is the reason why with this kind of cast, the runtime system checks before the assignment whether the current content of the source variable corresponds to the type requirements of the target variable. Otherwise, an exception that can be handled is triggered and the original value of the target variable remains the same. You can identify this exception of the error class CX_SY_MOVE_CAST_ERROR using the TRYENDTRY and the CATCH statement. Another way of preventing this runtime error is to use runtime type identification (RTTI) classes. You can use RTTI classes to determine the dynamic type at runtime and set a condition for the cast.

156

© Copyright . All rights reserved.

Unit 3 Exercise 10 Implement Down-Casts

Business Example As a developer, design an application where you want to know about the highest cargo load of all the cargo planes without knowing the details.  Template: SAPBC401_INH_T3 Solution: SAPBC401_INH_S3_OPT Determine the highest cargo value. 1. In the LCL_CARGO_PLANE class, define and implement the GET_CARGO public functional method to return the cargo value. Define a returning parameter RV_CARGO. 2. In the LCL_CARRIER class, define and implement the GET_MAX_CARGO private function method to calculate the highest cargo value (load capacity) of all cargo planes. Loop at the list of airplanes and use the down-cast technique to identify cargo planes. For those airplanes for which the down-cast was successful, you can then call the GET_CARGO method defined and implemented in the previous step. 3. Call the GET_MAX_CARGO method from within the DISPLAY_ATTRIBUTES method class LCL_CARRIER and output the result.

© Copyright . All rights reserved.

157

Unit 3 Solution 10 Implement Down-Casts

Business Example As a developer, design an application where you want to know about the highest cargo load of all the cargo planes without knowing the details.  Template: SAPBC401_INH_T3 Solution: SAPBC401_INH_S3_OPT Determine the highest cargo value. 1. In the LCL_CARGO_PLANE class, define and implement the GET_CARGO public functional method to return the cargo value. Define a returning parameter RV_CARGO. a) See the source code extract from the model solution. 2. In the LCL_CARRIER class, define and implement the GET_MAX_CARGO private function method to calculate the highest cargo value (load capacity) of all cargo planes. Loop at the list of airplanes and use the down-cast technique to identify cargo planes. For those airplanes for which the down-cast was successful, you can then call the GET_CARGO method defined and implemented in the previous step. a) See the source code extract from the model solution. 3. Call the GET_MAX_CARGO method from within the DISPLAY_ATTRIBUTES method class LCL_CARRIER and output the result. a) See the source code extract from the model solution. SAPBC401_INH_S3_OPT REPORT

sapbc401_inh_s3_opt.

TYPE-POOLS icon. ... *---------------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *---------------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. PUBLIC SECTION.

158

© Copyright . All rights reserved.

Lesson: Implementing Down-Casts Using Inheritance

METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype iv_cargo TYPE s_plan_car EXCEPTIONS wrong_planetype, display_attributes REDEFINITION, get_cargo RETURNING value(rv_cargo) TYPE s_plan_car. PRIVATE SECTION. DATA: mv_cargo TYPE s_plan_car. ENDCLASS.

"lcl_cargo_plane DEFINITION

*----------------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *----------------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. METHOD constructor. super->constructor( EXPORTING iv_name = iv_name iv_planetype = iv_planetype EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ENDIF. mv_cargo = iv_cargo. ENDMETHOD. "constructor METHOD display_attributes. super->display_attributes( ). WRITE: / 'Max Cargo:'(005), AT c_pos_1 mv_cargo LEFT-JUSTIFIED. ULINE. ENDMETHOD. "display_attributes METHOD get_cargo. rv_cargo = mv_cargo. ENDMETHOD. ENDCLASS.

"get_cargo

"lcl_cargo_plane IMPLEMENTATION

... *---------------------------------------------------* * CLASS lcl_carrier DEFINITION *---------------------------------------------------* CLASS lcl_carrier DEFINITION.

© Copyright . All rights reserved.

159

Unit 3: Inheritance and Casting

PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string, display_attributes, add_airplane IMPORTING io_plane TYPE REF TO lcl_airplane. PRIVATE SECTION. DATA: mv_name TYPE string, mt_airplanes TYPE TABLE OF REF TO lcl_airplane. METHODS: display_airplanes, get_max_cargo RETURNING value(rv_max_cargo) TYPE s_plan_car. ENDCLASS.

"lcl_carrier DEFINITION

*--------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *--------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. METHOD constructor. mv_name = iv_name. ENDMETHOD.

"constructor

METHOD display_attributes. DATA: lv_max_cargo TYPE s_plan_car. SKIP 2. WRITE: icon_flight AS ICON, mv_name. ULINE. ULINE. me->display_airplanes( ). lv_max_cargo = me->get_max_cargo( ). WRITE: / 'Capacity of biggest cargo plane:'(max), lv_max_cargo LEFT-JUSTIFIED. ENDMETHOD.

"display_attributes

METHOD add_airplane. APPEND io_plane TO mt_airplanes. ENDMETHOD. "add_airplane METHOD display_airplanes. DATA: lo_plane TYPE REF TO lcl_airplane. LOOP AT mt_airplanes INTO lo_plane. lo_plane->display_attributes( ).

160

© Copyright . All rights reserved.

Lesson: Implementing Down-Casts Using Inheritance

ENDLOOP. ENDMETHOD.

"display_airplanes

METHOD get_max_cargo. DATA: lo_plane TYPE REF TO lcl_airplane, lo_cargo TYPE REF TO lcl_cargo_plane. LOOP AT mt_airplanes INTO lo_plane. TRY. lo_cargo ?= lo_plane. IF rv_max_cargo < lo_cargo->get_cargo( ). rv_max_cargo = lo_cargo->get_cargo( ). ENDIF. *

CATCH cx_sy_move_cast_error. plane is not a cargo plane - do nothing ENDTRY. ENDLOOP. ENDMETHOD. "get_max_cargo

ENDCLASS.

"lcl_carrier IMPLEMENTATION

© Copyright . All rights reserved.

161

Unit 3: Inheritance and Casting

Correct Usage of Class Hierarchies

Figure 80: Usage of Class Hierarchies

As early as the modeling phase, you should be able to identify a generalization and specialization relationship between certain classes. If such a relationship exists between certain classes, you can use inheritance to represent this in ABAP Objects. For example, the semantics must be preserved when you redefine methods. Furthermore, inherited components must be used as intended in the superclass. Misuse of Inheritance

Figure 81: Examples – Misuse of Inheritance

If you do not have a correct understanding of the semantics of “is a (specific)”, you run the risk of identifying the wrong places in which to use inheritance. Sometimes the need for another attribute for a class is incorrectly answered with a specialization. For example, a superclass called Car, contains the subclasses red Car, blue Car, and so on. The statement “A red car is a specific car” is correct only at first glance. However, there are no cars without a color. At most, there are some cars that have not been painted. Therefore, every car needs the attribute color, assuming that it is relevant to the application. Therefore, the attribute should already have been defined in the superclass. There may be contradictions with reality when you try to implement a method for painting the cars.

162

© Copyright . All rights reserved.

Lesson: Implementing Down-Casts Using Inheritance

Note: Such attributes are also defined as reference variables to a superclass of role classes. There is one description class for each role. To change the role of an instance, you then exchange the references to the corresponding role description instances. Specialist literature also refers to this as a role design pattern. In some cases, specialization relationships that do not allow for semantics to be retained needs to be identified. For example, the square class inherits from the rectangle class. If you try to define methods for the rectangle that change the width and height separately, these methods will not make sense when applied to the square. Even if the methods are redefined to make the lengths of the sides uniform, the semantics will be different. For the same reason, that is, using inheritance only because some required functions are found in a super class is also not appropriate.

© Copyright . All rights reserved.

163

Unit 3: Inheritance and Casting

LESSON SUMMARY You should now be able to:

164



Implement down-casts using inheritance



Model class hierarchies

© Copyright . All rights reserved.

Unit 3 Learning Assessment

1. Which of the following is a relationship in which the subclass inherits all the main characteristics of the superclass? Choose the correct answer. X

A Specialization

X

B Generalization

X

C Polymorphism

X

D Casting

2. Which of the following are the characteristics of generalization and specialization? Choose the correct answers. X

A Common components only exist once in the superclass

X

B Components in the subclasses are available in all superclasses

X

C Subclasses contain extensions or changes

X

D Subclasses are not dependent on superclasses

3. Which of the following can be called automatically in the superclass? Choose the correct answer. X

A Method

X

B Instance constructor

X

C Static constructor

X

D Object

© Copyright . All rights reserved.

165

Unit 3: Learning Assessment

4. A superclass is a generalization of its subclasses. Determine whether this statement is true or false. X

True

X

False

5. Which of the following section is used to change superclasses without the need to know the subclasses? Choose the correct answer. X

A PROTECTED

X

B PRIVATE

X

C PUBLIC

6. A __________ can always have a static constructor. Choose the correct answer. X

A subclass

X

B superclass

X

C subclass and superclass

7. Which of the following is used to define the static type of reference variable? Choose the correct answer.

166

X

A APPEND

X

B CREATE OBJECT

X

C TYPE REF TO

X

D CLASS

© Copyright . All rights reserved.

Unit 3: Learning Assessment

8. Which of the following is determined by the assignment? Choose the correct answer. X

A Superclass

X

B Static type

X

C Dynamic type

X

D Subclass

9. Suppose that you have a class X that inherits from class Y. After an up-cast a reference variable that is statically typed TYPE REF TO Y points to an instance of class X. What components of class X can you access with this reference variable? Choose the correct answers. X

A Components defined in class X

X

B Components inherited from class Y

X

C Components redefined in class X

X

D Components defined in class X and redefined in its subclasses

10. When objects from different classes react differently to the same method calls, this is known as __________. Choose the correct answer. X

A objects

X

B events

X

C polymorphism

X

D inheritance

11. A typical use for ________ assignments is to prepare for generic access. Choose the correct answer. X

A events

X

B up-cast

X

C methods

X

D down-cast

© Copyright . All rights reserved.

167

Unit 3: Learning Assessment

12. Which of the following is used to assign a superclass reference to a subclass reference? Choose the correct answer. X

A Widening Cast

X

B Narrowing Cast

X

C Redefinition

13. Which of the following is the down-cast assignment operator? Choose the correct answer. X

A APPEND

X

B CATCH

X

C MOVE ... ?TO ...

X

D TRY-ENDTRY

14. Suppose you have the same class X that inherits from class Y. After a down-cast, a reference variable that statically typed TYPE REF TO X points to an instance of class X. Which of the following components of class X can you access with this reference variable? Choose the correct answers.

168

X

A Components defined in class X

X

B Components inherited from class Y

X

C Components redefined in class X

X

D Components defined in class X and redefined in its subclasses

X

E Components inherited and redefined from a ‘Friend’ relationship

© Copyright . All rights reserved.

Unit 3: Learning Assessment

15. Suppose a reference variable that is typed on an interface contains an instance reference of a class that implements this interface and you copy this to a reference variable that is typed on the class (down-cast). Which of the following components can you access with this reference variable? Choose the correct answers. X

A The components of the interface

X

B The components from the class that are not defined on the interface

X

C All components of the class

X

D The components of the interface for which alias names have been defined

X

E Components from a ‘Friend’ relationship

16. What are the advantages of correctly using class hierarchies? Choose the correct answers. X

A Centralized maintenance

X

B Safe and generic method of access

X

C Semantics preserved

X

D Intended use of inherited components

© Copyright . All rights reserved.

169

Unit 3 Learning Assessment - Answers

1. Which of the following is a relationship in which the subclass inherits all the main characteristics of the superclass? Choose the correct answer. X

A Specialization

X

B Generalization

X

C Polymorphism

X

D Casting

2. Which of the following are the characteristics of generalization and specialization? Choose the correct answers. X

A Common components only exist once in the superclass

X

B Components in the subclasses are available in all superclasses

X

C Subclasses contain extensions or changes

X

D Subclasses are not dependent on superclasses

3. Which of the following can be called automatically in the superclass? Choose the correct answer.

170

X

A Method

X

B Instance constructor

X

C Static constructor

X

D Object

© Copyright . All rights reserved.

Unit 3: Learning Assessment - Answers

4. A superclass is a generalization of its subclasses. Determine whether this statement is true or false. X

True

X

False

5. Which of the following section is used to change superclasses without the need to know the subclasses? Choose the correct answer. X

A PROTECTED

X

B PRIVATE

X

C PUBLIC

6. A __________ can always have a static constructor. Choose the correct answer. X

A subclass

X

B superclass

X

C subclass and superclass

7. Which of the following is used to define the static type of reference variable? Choose the correct answer. X

A APPEND

X

B CREATE OBJECT

X

C TYPE REF TO

X

D CLASS

© Copyright . All rights reserved.

171

Unit 3: Learning Assessment - Answers

8. Which of the following is determined by the assignment? Choose the correct answer. X

A Superclass

X

B Static type

X

C Dynamic type

X

D Subclass

9. Suppose that you have a class X that inherits from class Y. After an up-cast a reference variable that is statically typed TYPE REF TO Y points to an instance of class X. What components of class X can you access with this reference variable? Choose the correct answers. X

A Components defined in class X

X

B Components inherited from class Y

X

C Components redefined in class X

X

D Components defined in class X and redefined in its subclasses

10. When objects from different classes react differently to the same method calls, this is known as __________. Choose the correct answer.

172

X

A objects

X

B events

X

C polymorphism

X

D inheritance

© Copyright . All rights reserved.

Unit 3: Learning Assessment - Answers

11. A typical use for ________ assignments is to prepare for generic access. Choose the correct answer. X

A events

X

B up-cast

X

C methods

X

D down-cast

12. Which of the following is used to assign a superclass reference to a subclass reference? Choose the correct answer. X

A Widening Cast

X

B Narrowing Cast

X

C Redefinition

13. Which of the following is the down-cast assignment operator? Choose the correct answer. X

A APPEND

X

B CATCH

X

C MOVE ... ?TO ...

X

D TRY-ENDTRY

© Copyright . All rights reserved.

173

Unit 3: Learning Assessment - Answers

14. Suppose you have the same class X that inherits from class Y. After a down-cast, a reference variable that statically typed TYPE REF TO X points to an instance of class X. Which of the following components of class X can you access with this reference variable? Choose the correct answers. X

A Components defined in class X

X

B Components inherited from class Y

X

C Components redefined in class X

X

D Components defined in class X and redefined in its subclasses

X

E Components inherited and redefined from a ‘Friend’ relationship

15. Suppose a reference variable that is typed on an interface contains an instance reference of a class that implements this interface and you copy this to a reference variable that is typed on the class (down-cast). Which of the following components can you access with this reference variable? Choose the correct answers. X

A The components of the interface

X

B The components from the class that are not defined on the interface

X

C All components of the class

X

D The components of the interface for which alias names have been defined

X

E Components from a ‘Friend’ relationship

16. What are the advantages of correctly using class hierarchies? Choose the correct answers.

174

X

A Centralized maintenance

X

B Safe and generic method of access

X

C Semantics preserved

X

D Intended use of inherited components

© Copyright . All rights reserved.

UNIT 4

Interfaces and Casting

Lesson 1 Defining and Implementing Local Interfaces Exercise 11: Define and Implement a Local Interface

176 181

Lesson 2 Implement Polymorphism Using Interfaces Exercise 12: Implement Polymorphism Using Interfaces

191 195

Lesson 3 Joining Classmodels Using Interfaces Exercise 13: Integrate Class Models Using Interfaces

202 205

UNIT OBJECTIVES ●

Explain the usage areas for interfaces



Create generalization and specialization relationships using interfaces



Implement polymorphism using interfaces



Implement down-casts with interfaces



Integrate different submodels using interfaces



Create and use interface hierarchies

© Copyright . All rights reserved.

175

Unit 4 Lesson 1 Defining and Implementing Local Interfaces

LESSON OVERVIEW This lesson explains the method of defining and implementing interfaces. Business Example As a developer, you need to create interfaces and implement them in your model in ABAP objects. For this reason, you require the following knowledge: ●

An understanding of interface use



An understanding of interface definition



An understanding of interface implementation

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Explain the usage areas for interfaces



Create generalization and specialization relationships using interfaces

Areas of Use for Interfaces

Figure 82: Central Definition of Shared Components

176

© Copyright . All rights reserved.

Lesson: Defining and Implementing Local Interfaces

Interfaces differ from regular inheritance in their areas of use. However, in terms of programming, there are hardly any differences between interfaces and regular inheritance. Interfaces are superclasses that cannot be instantiated, do not contain implementations, and have only public components. You can simulate multiple inheritances using interfaces. In ABAP Objects, interfaces primarily serve to define uniform interface protocols for services. Various classes can implement these services in different ways, but you need to keep the same semantics. Therefore, interfaces contain no implementations. In ABAP Objects, the same components can generally be defined in interfaces and classes. To recognize the semantic differences from regular inheritance, you can concentrate on the following use cases. For example, you want to allow multiple classes to implement a service in different ways, but using the same method names and a uniform signature. With regular inheritance, you would define such a method in the shared superclass. However, if you cannot model a superclass for inheritance suitably, you need to define an interface and then define the method in the interface. Therefore, you can compare this case with a generalization relationship within a superclass.

Protocol Definition by Client

Figure 83: Client Defines The Protocoll

Compared to regular inheritance, the distribution of roles in interfaces is sometimes different. The user generally defines the interfaces. In these interfaces, the user describes both technically and semantically the services that the user wants the providers to offer. Each class can now decide for itself whether it serves the interface, that is, whether it actually offers the services defined in the interface. Therefore, this case is similar to a specialization relationship with a subclass. As with regular inheritance, access to these services defined in the interface is then usually generic, that is, access to the services uses a reference that is typed on the interface. As in inheritance, polymorphism can also be implemented in interfaces.

© Copyright . All rights reserved.

177

Unit 4: Interfaces and Casting

Generic Access to Interface Components

Figure 84: Interfaces in UML Notation

In Unified Modeling Language (UML), you represent the interfaces in the same way as you represent classes. However, in addition to the interface’s name, you use notation «interface».  You represent the use of an interface by a dotted line with a two-sided arrow from the user to the interface. The keyword «uses» is optional.

Create Generalization and Specialization Relationships Using Interfaces

Figure 85: Defining and Implementing an Interface

178

© Copyright . All rights reserved.

Lesson: Defining and Implementing Local Interfaces

In ABAP Objects, you can define the same components in an interface as you can in classes. However, interfaces do not know the visibility levels of their components, that is, all the components of an interface are public. Classes implement interfaces in the following ways: Interface name



The interface name is listed in the definition part of the class with the INTERFACES statement. This occurs in the PUBLIC SECTION, that is, interfaces can only be implemented publicly. ●

Interface methods The interface methods are implemented in the implementation part of the class.



Interface components The components defined in the interface are addressed in the implementation part of the class.

Interface components are distinguished from the other components in the implementing class by prefixing the interface name followed by a tilde (~), which is the interface resolution operator. interface_name~component_name To simplify access to interface components, you can use alias names. These alias names can appear in the definition part of a class or in the interface definition. The use of alias names is subject to the visibility restriction of the defining class. An alias for an interface method is as follows: ALIASES a_1 FOR lif_1~method_1. The interface method lif_1~method_1 can be addressed with the shorter form ref->a_1.

Access to Interface Components

Figure 86: Addressing Interface Components Using Object References

© Copyright . All rights reserved.

179

Unit 4: Interfaces and Casting

You can access interface components only by using an object reference whose class implements the interface. You use the interface resolution operator (~) to access the interface components in the implementation part of the class. Alternatively, you can use the alias names defined in the implementing class for the interface components. Even if shared components of the implementing classes are subsequently transferred to the interface, access to these components does not need to be adapted.

180

© Copyright . All rights reserved.

Unit 4 Exercise 11 Define and Implement a Local Interface

Business Example You need to add a car rental company to your program. The car rental company together with the existing airline needs to be added into the travel agency class as the travel agency’s business partners. To add these business partners, you need a generic access to airlines and car rental companies. Instead of defining a common superclass, you need to define an interface with generic services, which is then implemented in the classes for airlines and car rental companies. Define and implement the interface in your existing class for airlines. Template: SAPBC401_INH_S3 Solution: SAPBC401_INT_S1 Task 1 To increase the legibility of your program, split the source code into a main program and one INCLUDE program. The INCLUDE program must contain all the local class definitions and implementations. The declaration of reference variables and the START-OF-SELECTION event block should remain in the main program.

Note: This distribution does not follow the recommended use of INCLUDES in ABAP programs. According to the programming guidelines, the class definitions and data declarations should go to the TOP-INCLUDE, the implementations to a P-INCLUDE, and the START-OF-SELECTION event block to an E-INCLUDE. 1. Complete your program ZBC401_##_MAIN (## is your two-digit group number) or copy the sample solution from the previous exercise. 2. In your main program, implement the usage of a new INCLUDE program (recommended name: ZBC401_##_CARRIER with ## being your two-digit group number). Create the INCLUDE through forward navigation. You can do this by double-clicking the INCLUDE’s name. 3. Cut the definition and implementation sections of all four local classes from the main program and paste them on to the newly created include program.

© Copyright . All rights reserved.

181

Unit 4: Interfaces and Casting

4. Where do you have to place the INCLUDE statement to avoid syntax errors?

5. Activate and test your program.

Task 2 Define an interface with the DISPLAY_PARTNER method in order to later offer generic access options to potential clients in the travel agency example. 1. Create a new INCLUDE (recommended name: ZBC401_##_AGENCY with ## being your twodigit group number) and define an interface LIF_PARTNER in the new INCLUDE. 2. The interface should contain the DISPLAY_PARTNER instance method. The instance method should not have any parameters. Later , your task will be to display business partner attributes. Check the entire program for syntactical correctness and activate it. Task 3 The LCL_CARRIER class should make the services defined in the interface available to potential clients. To achieve this, class LCL_CARRIER needs to implement the interface and therefore the interface method DISPLAY_PARTNER. 1. In the definition of LCL_CARRIER, declare the newly created interface. 2. Implement the coding of the DISPLAY_PARTNER interface method in the LCL_CARRIER class. As is evident from the name of the method, the data or attributes of this business partner should be displayed here. Consider the possible solutions and execute the most suitable approach. Check the entire application for syntactical correctness and activate your application. Hint: The performance of the application will still not change at this point; the results can be seen only in the later tasks.

Task 4 Test the interface implemented in the LCL_CARRIER class by calling the interface method from the main program. 1. In the main program, remove the call for the DISPLAY_ATTRIBUTES method of the LCL_CARRIER class. Replace it with a call for the DISPLAY_PARTNER interface method.

182

© Copyright . All rights reserved.

Lesson: Defining and Implementing Local Interfaces

2. What would be the objective of such a call at this point of the exercise be, or in other words, what does the option of this interface method call bring out of the main program in contrast with a conventional method call?

3. After a successful test, turn this method call into a comment so that it becomes ineffective. Hint: The generic use of the interface methods with another class takes place in the next steps of the exercise. The performance of the entire application will still not change at this point; the results can be seen only in later tasks.

© Copyright . All rights reserved.

183

Unit 4 Solution 11 Define and Implement a Local Interface

Business Example You need to add a car rental company to your program. The car rental company together with the existing airline needs to be added into the travel agency class as the travel agency’s business partners. To add these business partners, you need a generic access to airlines and car rental companies. Instead of defining a common superclass, you need to define an interface with generic services, which is then implemented in the classes for airlines and car rental companies. Define and implement the interface in your existing class for airlines. Template: SAPBC401_INH_S3 Solution: SAPBC401_INT_S1 Task 1 To increase the legibility of your program, split the source code into a main program and one INCLUDE program. The INCLUDE program must contain all the local class definitions and implementations. The declaration of reference variables and the START-OF-SELECTION event block should remain in the main program.

Note: This distribution does not follow the recommended use of INCLUDES in ABAP programs. According to the programming guidelines, the class definitions and data declarations should go to the TOP-INCLUDE, the implementations to a P-INCLUDE, and the START-OF-SELECTION event block to an E-INCLUDE. 1. Complete your program ZBC401_##_MAIN (## is your two-digit group number) or copy the sample solution from the previous exercise. a) Carry out this step in the usual manner. Additional information about the copying of programs is available in the SAP Library. 2. In your main program, implement the usage of a new INCLUDE program (recommended name: ZBC401_##_CARRIER with ## being your two-digit group number). Create the INCLUDE through forward navigation. You can do this by double-clicking the INCLUDE’s name. a) See the source text excerpt from the model solution.

184

© Copyright . All rights reserved.

Lesson: Defining and Implementing Local Interfaces

3. Cut the definition and implementation sections of all four local classes from the main program and paste them on to the newly created include program. a) See the source text excerpt from the model solution. 4. Where do you have to place the INCLUDE statement to avoid syntax errors? The INCLUDE statement has to be placed before the declaration of reference variables. Otherwise, the class definitions are not known in the declaration of reference variables. 5. Activate and test your program. a) Carry out this step in the usual manner. Additional information about the copying of programs is available in the SAP Library.

Task 2 Define an interface with the DISPLAY_PARTNER method in order to later offer generic access options to potential clients in the travel agency example. 1. Create a new INCLUDE (recommended name: ZBC401_##_AGENCY with ## being your twodigit group number) and define an interface LIF_PARTNER in the new INCLUDE. a) See the source text excerpt from the model solution. 2. The interface should contain the DISPLAY_PARTNER instance method. The instance method should not have any parameters. Later , your task will be to display business partner attributes. Check the entire program for syntactical correctness and activate it. a) See the source text excerpt from the model solution. Task 3 The LCL_CARRIER class should make the services defined in the interface available to potential clients. To achieve this, class LCL_CARRIER needs to implement the interface and therefore the interface method DISPLAY_PARTNER. 1. In the definition of LCL_CARRIER, declare the newly created interface. a) See the source text excerpt from the model solution. 2. Implement the coding of the DISPLAY_PARTNER interface method in the LCL_CARRIER class. As is evident from the name of the method, the data or attributes of this business partner should be displayed here. Consider the possible solutions and execute the most suitable approach. Check the entire application for syntactical correctness and activate your application. Hint: The performance of the application will still not change at this point; the results can be seen only in the later tasks. a) See the source text excerpt from the model solution.

© Copyright . All rights reserved.

185

Unit 4: Interfaces and Casting

Task 4 Test the interface implemented in the LCL_CARRIER class by calling the interface method from the main program. 1. In the main program, remove the call for the DISPLAY_ATTRIBUTES method of the LCL_CARRIER class. Replace it with a call for the DISPLAY_PARTNER interface method. a) See the source text excerpt from the model solution. 2. What would be the objective of such a call at this point of the exercise be, or in other words, what does the option of this interface method call bring out of the main program in contrast with a conventional method call? Apart from the detailed and longer syntax of this call, the interface method’s call can be replaced by an ordinary instance method call from, for example, DISPLAY_ATTRIBUTES. At this point in the exercise, this call does not seem altogether sensible. 3. After a successful test, turn this method call into a comment so that it becomes ineffective. Hint: The generic use of the interface methods with another class takes place in the next steps of the exercise. The performance of the entire application will still not change at this point; the results can be seen only in later tasks. a) See the source text excerpt from the model solution. Main program: SAPBC401_INT_S1 REPORT

sapbc401_int_s1.

TYPE-POOLS icon. INCLUDE bc401_int_s1_agency. INCLUDE bc401_int_s1_carrier. DATA: go_carrier go_airplane go_cargo go_passenger gv_count

TYPE TYPE TYPE TYPE TYPE

REF REF REF REF i.

TO TO TO TO

lcl_carrier, lcl_airplane, lcl_cargo_plane, lcl_passenger_plane,

START-OF-SELECTION. ******************* ***** Create Carrier ************************************ CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly-Travel'. ***** Passenger Plane

186

© Copyright . All rights reserved.

Lesson: Defining and Implementing Local Interfaces

CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. go_carrier->add_airplane( go_passenger ). ENDIF. ***** cargo Plane CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. go_carrier->add_airplane( go_cargo ). ENDIF. *** output carrier (including list of airplanes) * only for testing: * call interface method for the carrier *

go_carrier->lif_partner~display_partner( ). go_carrier->display_attributes( ). Include BC401_INT_S1_AGENCY

INTERFACE lif_partner. METHODS display_partner. ENDINTERFACE. Include BC401_INT_S1_CARRIER *---------------------------------------------------* * CLASS lcl_airplane DEFINITION *---------------------------------------------------* CLASS lcl_airplane DEFINITION. ... ENDCLASS. "lcl_airplane DEFINITION *---------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *---------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. ... ENDCLASS. "lcl_airplane IMPLEMENTATION *----------------------------------------------------*

© Copyright . All rights reserved.

187

Unit 4: Interfaces and Casting

* CLASS lcl_cargo_plane DEFINITION *----------------------------------------------------* * *----------------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS. "lcl_cargo_plane DEFINITION *--------------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *--------------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. ... ENDCLASS. "lcl_cargo_plane IMPLEMENTATION *--------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *--------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS. "lcl_passenger_plane DEFINITION *---------------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *---------------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. ... ENDCLASS.

"lcl_passenger_plane IMPLEMENTATION

*----------------------------------------------------* * CLASS lcl_carrier DEFINITION *----------------------------------------------------* CLASS lcl_carrier DEFINITION. PUBLIC SECTION. INTERFACES: lif_partner. METHODS: constructor IMPORTING iv_name TYPE string, display_attributes, add_airplane IMPORTING io_plane TYPE REF TO lcl_airplane. PRIVATE SECTION. DATA: mv_name TYPE string, mt_airplanes TYPE TABLE OF REF TO lcl_airplane.

188

© Copyright . All rights reserved.

Lesson: Defining and Implementing Local Interfaces

METHODS: display_airplanes. ENDCLASS.

"lcl_carrier DEFINITION

*---------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *---------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. METHOD constructor. mv_name = iv_name. ENDMETHOD. "constructor METHOD display_attributes. SKIP 2. WRITE: icon_flight AS ICON, mv_name. ULINE. ULINE. me->display_airplanes( ). ENDMETHOD. "display_attributes METHOD add_airplane. APPEND io_plane TO mt_airplanes. ENDMETHOD. "add_airplane METHOD display_airplanes. DATA: lo_plane TYPE REF TO lcl_airplane. LOOP AT mt_airplanes INTO lo_plane. lo_plane->display_attributes( ). ENDLOOP. ENDMETHOD. "display_airplanes METHOD lif_partner~display_partner. me->display_attributes( ). ENDMETHOD. "lif_partner~display_partner ENDCLASS.

"lcl_carrier IMPLEMENTATION

© Copyright . All rights reserved.

189

Unit 4: Interfaces and Casting

LESSON SUMMARY You should now be able to:

190



Explain the usage areas for interfaces



Create generalization and specialization relationships using interfaces

© Copyright . All rights reserved.

Unit 4 Lesson 2 Implement Polymorphism Using Interfaces

LESSON OVERVIEW This lesson explains polymorphism and implementing polymorphism using interfaces. Business Example As a developer, you need to create interfaces and implement polymorphism in your ABAP Objects project. For this reason, you require the following knowledge: ●

An understanding of polymorphism



An understanding of polymorphism in interface implementation

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Implement polymorphism using interfaces

Polymorphism with Interfaces

Figure 87: Up-Cast with Interface References

An interface reference can only refer to instances of classes that have implemented the interface because interfaces themselves cannot be instantiated. As in regular inheritance, you must use up-cast to copy a reference to the interface reference variable  to perform polymorphism with interfaces.

© Copyright . All rights reserved.

191

Unit 4: Interfaces and Casting

If the class has implemented the interface, it is certain that all the components that can be accessed syntactically after the cast assignment are available in the instance. A user can address the instance of the implementing class using the interface. The prefixing of the interface name and the interface resolution operator is omitted. However, the user is restricted to using the components from the interface. In the example, the DISPLAY_PARTNER and CHECK_AVAILABILITY methods of the LIF_PARTNER interface can be accessed only after assigning the reference variable GO_PARTNER. It is not possible to access the specific components of the instance from the LCL_RENTAL (GET_NAME in the above example) class using the GO_PARTNER reference variable. Therefore, the view is narrowed or, atleast, remains unchanged. That is why you describe this type of assignment of reference variables as up-cast. There is a switch from a view of several components to a view of only a few components. The target reference can, of course, accept more dynamic types after the assignment, than it could before. Therefore, the term widening cast is also suitable.

Generic Access with Interfaces

Figure 88: Row Type of the Internal Table in the Application Example

A typical area of use for up-cast assignments is preparation for generic access. A user who is not interested in the finer points of the instances of the class that implement the interface but who simply wants to address the components defined in the interface, could use an interface reference for this access. In the example shown, a travel agency (LCL_TRAVEL_AGENCY) needs to manage the various kinds of business partners in one list. You must therefore assign the row type of the internal table as the reference to the interface LIF_PARTNER. The travel agency only wants to request the services in order to display their attributes and check their availability. The relevant DISPLAY_PARTNER and CHECK_AVAILABILITY methods are defined in the LIF_PARTNER interface and implemented in all business partner classes.

192

© Copyright . All rights reserved.

Lesson: Implement Polymorphism Using Interfaces

The objects of different classes (LCL_HOTEL, LCL_RENTAL, and LCL_CARRIER in the example) can be kept in an internal table, typed with interface references (LIF_PARTNER in the example). The components defined in the interface can then be accessed uniformly. For this example, the ADD_PARTNER method is needed. This method copies the references to all kinds of business partners in the internal table. The import parameter of this method is already typed as the reference to the interface. Polymorphism – Generic Access Using the Interface Reference

Figure 89: Polymorphism – Generic Access Using the Interface Reference

Polymorphism can also be performed for interfaces. You can use interface references to call methods and execute different implementations depending on the object of the reference. The dynamic type of the reference variable is used to search for the implementation of a method. In the above example, lo_partner->display_partner( ) uses the class of the instance to which go_partner actually refers in order to search for the implementation of display_partner. The implementation that is executed when DISPLAY_PARTNER is called now depends on the object to which the interface reference lo_partner currently refers. When objects from different classes react differently to the same method calls, it is known as polymorphism. The option of performing polymorphism is one of the main strengths of interfaces. A client can handle different classes uniformly, regardless of their implementation. The runtime system searches for the right implementation of a method on behalf of the client. Polymorphism can be used to write programs that are highly generic, that is, they do not need to be changed significantly if use cases are added. In the example, it becomes easy to add a class for boat rentals. For example, the relevant class with the name LCL_SHIPPING will simply have to implement the LIF_PARTNER interface and the DISPLAY_PARTNER method defined there. Business partner management can then easily include ship-owning companies and request them to display their attributes.

© Copyright . All rights reserved.

193

Unit 4: Interfaces and Casting

194

© Copyright . All rights reserved.

Unit 4 Exercise 12 Implement Polymorphism Using Interfaces Business Example You need to add a class that uses the previously defined interface. Travel agencies need to manage various business partners using the interface and access general services of the business partners. Template: SAPBC401_INH_T2 Solution: SAPBC401_INT_S2 Task 1 Define a local class for travel agencies. 1. Complete your program ZBC401_##_MAIN (## is your two-digit group number) or copy the template program with all its INCLUDES. 2. In the INCLUDE program that contains the definition of the LIF_PARTNER interface, define and implement the LCL_TRAVEL_AGENCY local class. Hint: If you have not copied the template program, you can reduce your typing load by copying the definition and implementation of the LCL_TRAVEL_AGENCY class from the SAPBC401_INT_T2 template and include BC401_INT_T2_AGENCY. You can also create the LCL_TRAVEL_AGENCY class from scratch, without using templates. 3. As a private class attribute, add an internal table MT_PARTNERS for the buffering of references to the business partners who have implemented the LIF_PARTNER interface. 4. Define and implement a public method named ADD_PARTNER so that the business partner references can be added to the MT_PARTNERS list. Define an import parameter named IO_PARTNER  with an appropriate type. 5. Extend the implementation of the DISPLAY_ATTRIBUTES method in a way that it not only displays information about the travel agency but also about its business partners. Use the previously defined DISPLAY_PARTNERS method.

Task 2

© Copyright . All rights reserved.

195

Unit 4: Interfaces and Casting

In the main program, generate a travel agency instance, transfer the references to the airline to this instance, and add the attributes. 1. In the main program, define a suitably typed reference variable for your new travel agency class. 2. Using the reference, generate an instance of your class LCL_TRAVEL_AGENCY. Decide how to fill out the attributes. 3. Call the ADD_PARTNER method to transfer the references to the generated airline instances to the travel agency. 4. Display the attributes of the travel agency (including information about its business partners) by calling its method DISPLAY_ATTRIBUTES.

196

© Copyright . All rights reserved.

Unit 4 Solution 12 Implement Polymorphism Using Interfaces Business Example You need to add a class that uses the previously defined interface. Travel agencies need to manage various business partners using the interface and access general services of the business partners. Template: SAPBC401_INH_T2 Solution: SAPBC401_INT_S2 Task 1 Define a local class for travel agencies. 1. Complete your program ZBC401_##_MAIN (## is your two-digit group number) or copy the template program with all its INCLUDES. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 2. In the INCLUDE program that contains the definition of the LIF_PARTNER interface, define and implement the LCL_TRAVEL_AGENCY local class. Hint: If you have not copied the template program, you can reduce your typing load by copying the definition and implementation of the LCL_TRAVEL_AGENCY class from the SAPBC401_INT_T2 template and include BC401_INT_T2_AGENCY. You can also create the LCL_TRAVEL_AGENCY class from scratch, without using templates. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 3. As a private class attribute, add an internal table MT_PARTNERS for the buffering of references to the business partners who have implemented the LIF_PARTNER interface. a) See the source text excerpt from the model solution. 4. Define and implement a public method named ADD_PARTNER so that the business partner references can be added to the MT_PARTNERS list. Define an import parameter named IO_PARTNER  with an appropriate type. a) See the source text excerpt from the model solution.

© Copyright . All rights reserved.

197

Unit 4: Interfaces and Casting

5. Extend the implementation of the DISPLAY_ATTRIBUTES method in a way that it not only displays information about the travel agency but also about its business partners. Use the previously defined DISPLAY_PARTNERS method. a) See the source text excerpt from the model solution.

Task 2 In the main program, generate a travel agency instance, transfer the references to the airline to this instance, and add the attributes. 1. In the main program, define a suitably typed reference variable for your new travel agency class. a) See the source text excerpt from the model solution. 2. Using the reference, generate an instance of your class LCL_TRAVEL_AGENCY. Decide how to fill out the attributes. a) See the source text excerpt from the model solution. 3. Call the ADD_PARTNER method to transfer the references to the generated airline instances to the travel agency. a) See the source text excerpt from the model solution. 4. Display the attributes of the travel agency (including information about its business partners) by calling its method DISPLAY_ATTRIBUTES. a) See the source text excerpt from the model solution. Include BC401_INT_S2_AGENCY *&-------------------------------------------------* *& Include BC401_INT_S2_AGENCY *&-------------------------------------------------* INTERFACE lif_partner. METHODS: display_partner. ENDINTERFACE. "lif_partner *--------------------------------------------------* * CLASS lcl_travel_agency DEFINITION *--------------------------------------------------* CLASS lcl_travel_agency DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string, add_partner IMPORTING io_partner TYPE REF TO lif_partner, display_agency_partners, display_attributes.

198

© Copyright . All rights reserved.

Lesson: Implement Polymorphism Using Interfaces

PRIVATE SECTION. DATA: mv_name TYPE string, mt_partners TYPE TABLE OF REF TO lif_partner. ENDCLASS.

"lcl_travel_agency DEFINITION

*---------------------------------------------------* * CLASS lcl_travel_agency IMPLEMENTATION *---------------------------------------------------* CLASS lcl_travel_agency IMPLEMENTATION. METHOD display_attributes. WRITE: / icon_private_files AS ICON, 'Travel Agency:'(007), mv_name. ULINE. display_agency_partners( ). ENDMETHOD. "display_attributes METHOD display_agency_partners. DATA: lo_partner TYPE REF TO lif_partner. WRITE 'Here are the partners of the travel agency:'(008). ULINE. LOOP AT mt_partners INTO lo_partner. lo_partner->display_partner( ). ENDLOOP. ENDMETHOD.

"display_agency_partners

METHOD constructor. mv_name = iv_name. ENDMETHOD. "constructor METHOD add_partner. APPEND io_partner TO mt_partners. ENDMETHOD. "add_partner ENDCLASS.

"lcl_travel_agency IMPLEMENTATION Main Program SAPBC401_INT_S2

REPORT

sapbc401_int_s2.

TYPE-POOLS icon. INCLUDE bc401_int_s2_agency. INCLUDE bc401_int_s2_carrier. DATA: go_agency go_carrier go_airplane go_cargo go_passenger gv_count

TYPE TYPE TYPE TYPE TYPE TYPE

© Copyright . All rights reserved.

REF REF REF REF REF i.

TO TO TO TO TO

lcl_travel_agency, lcl_carrier, lcl_airplane, lcl_cargo_plane, lcl_passenger_plane,

199

Unit 4: Interfaces and Casting

START-OF-SELECTION. ******************* ***** create travel_agency CREATE OBJECT go_agency EXPORTING iv_name = 'Travel&Smile Travel'. ***** Create Carrier CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly Travel'. ***** Insert carrier into business partner list of ***** travel agency go_agency->add_partner( go_carrier ). ***** Passenger Plane CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. go_carrier->add_airplane( go_passenger ). ENDIF. ***** cargo Plane CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. go_carrier->add_airplane( go_cargo ). ENDIF. ***** show attributes of all partners of ***** travel agency go_agency->display_attributes( ).

200

© Copyright . All rights reserved.

Lesson: Implement Polymorphism Using Interfaces

LESSON SUMMARY You should now be able to: ●

Implement polymorphism using interfaces

© Copyright . All rights reserved.

201

Unit 4 Lesson 3 Joining Classmodels Using Interfaces

LESSON OVERVIEW This lesson explains the method of joining classmodels using interfaces. Business Example As a developer, you need to integrate multiple class models  of your ABAP Objects project. For this reason, you require the following knowledge: ●

An understanding of submodels



An understanding of integrating submodels



An understanding of interface hierarchies

LESSON OBJECTIVES After completing this lesson, you will be able to:

202



Implement down-casts with interfaces



Integrate different submodels using interfaces



Create and use interface hierarchies

© Copyright . All rights reserved.

Lesson: Joining Classmodels Using Interfaces

Down-Casts with Interfaces

Figure 90: Down-Cast Assignment and Exception Handling in the Application Example

To assign an interface reference to a class reference where the class has implemented the interface, you must use the down-cast assignment operator MOVE ... ?TO ... or its short form ?=. Otherwise, the system would return a message stating that it is not certain that all components that can be accessed syntactically after the cast assignment are actually available in the instance. As a rule, the implementing class contains more components than the interface. Interface reference variables can contain references to instances of the implementing class at runtime. After assigning this type of reference back to a reference to the implementing class, clients are no longer limited to interface components. This type of reference variable assignment  is described as down-casting.  The down-casting view  is usually widened or at least unchanged. This is a switch from a view of a few components to a view of more components. The term Narrowing Cast is also used. A typical area of use for down-cast assignments is when specific components of instances need to be addressed whose references are kept in variables that are typed on the interface. A user who is interested in the finer points of the instances in implementing classes cannot use the interface reference because the downcast assignment  only allows access to the interface components. In the example shown here,a travel agency (LCL_TRAVEL_AGENCY) needs to book a flight but keeps all the various business partner references in an internal table that was typed on the interface LIF_PARTNER. What happens if there is no airline reference in the interface reference GO_PARTNER at runtime, but the down-cast assignment operator is used to copy the reference to the then-invalid reference GO_CARRIER? In contrast to the up-cast assignment, it is possible that the static type of the target variable(GO_CARRIER) is neither more general than nor the same as the dynamic type of the source variables (GO_PARTNER), specifically if GO_PARTNER contains hotel or car rental references.

© Copyright . All rights reserved.

203

Unit 4: Interfaces and Casting

The runtime system checks this type of cast before the assignment, whether or not the current content of the source variable corresponds to the type requirements of the target variable. Otherwise, an exception that can be handled is triggered, and the original value of the target variable remains the same.This exception of error class CX_SY_MOVE_CAST_ERROR can be identified using TRY-ENDTRY and the CATCH statement. Another way to prevent this runtime error would be to use runtime type identification (RTTI) classes. They can be used to determine the dynamic type atruntime and to set a condition for the cast. Assignments between interface reference variables, whose typing interfaces are not related to each other, cannot be checked statically and must therefore be performed using down-cast. With such an assignment, the system checks at runtime whether the class of the instance to which the source reference refers also supports the interface with which the target reference is typed.

204

© Copyright . All rights reserved.

Unit 4 Exercise 13 Integrate Class Models Using Interfaces

Business Example You need to add the car rental company with its vehicles to your own object model. By implementing the already defined interface, you can ensure that the car rental company can be added to the list of business partners of the travel agency. Template: SAPBC401_INT_T3 Solution: SAPBC401_INT_S3 Task 1 Copy the definitions and implementations of classes LCL_RENTAL and the vehicle classes (LCL_VEHICLE, LCL_TRUCK, and LCL_BUS) to your program and create instances of these classes. 1. Complete your program ZBC401_##_MAIN (## is your two-digit group number) or copy the template program with all its INCLUDES. 2. If you have copied the template program, analyze it and continue with the next task. If you want to continue working with your own program then first copy INCLUDE program BC401_INT_T3_RENTAL (recommended name: ZBC401_##_RENTAL, where ## is your twodigit group number) and make the new INCLUDE program part of your own program. 3. In your main program, create an instance of LCL_RENTAL and a number of instances of vehicle classes. Add all the vehicles to the rental company’s list of vehicles by calling method ADD_VEHICLE of LCL_RENTAL. Hint: To reduce the typing effort you can copy and paste the relevant coding from the main program of SAPBC401_INT_T3.

Task 2 Implement interface LIF_PARTNER in class LCL_RENTAL. 1. Call method ADD_PARTNER to add the instance of LCL_RENTAL to the travel agency’s list of business partners.

© Copyright . All rights reserved.

205

Unit 4: Interfaces and Casting

2. Perform a syntax check. Why does this method call cause a syntax error?

3. Go to the definition part of class LCL_RENTAL and declare the implementation of interface LIF_PARTNER. 4. Provide an implementation of the method defined in the interface. 5. Activate the INCLUDE with the definition and implementation of LCL_RENTAL. Then go to the main program and perform another syntax check Why does the call of ADD_PARTNER now work for the car rental company?

206

© Copyright . All rights reserved.

Unit 4 Solution 13 Integrate Class Models Using Interfaces

Business Example You need to add the car rental company with its vehicles to your own object model. By implementing the already defined interface, you can ensure that the car rental company can be added to the list of business partners of the travel agency. Template: SAPBC401_INT_T3 Solution: SAPBC401_INT_S3 Task 1 Copy the definitions and implementations of classes LCL_RENTAL and the vehicle classes (LCL_VEHICLE, LCL_TRUCK, and LCL_BUS) to your program and create instances of these classes. 1. Complete your program ZBC401_##_MAIN (## is your two-digit group number) or copy the template program with all its INCLUDES. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 2. If you have copied the template program, analyze it and continue with the next task. If you want to continue working with your own program then first copy INCLUDE program BC401_INT_T3_RENTAL (recommended name: ZBC401_##_RENTAL, where ## is your twodigit group number) and make the new INCLUDE program part of your own program. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 3. In your main program, create an instance of LCL_RENTAL and a number of instances of vehicle classes. Add all the vehicles to the rental company’s list of vehicles by calling method ADD_VEHICLE of LCL_RENTAL. Hint: To reduce the typing effort you can copy and paste the relevant coding from the main program of SAPBC401_INT_T3. a) See the source text excerpt from the model solution.

Task 2 Implement interface LIF_PARTNER in class LCL_RENTAL.

© Copyright . All rights reserved.

207

Unit 4: Interfaces and Casting

1. Call method ADD_PARTNER to add the instance of LCL_RENTAL to the travel agency’s list of business partners. a) See the source text excerpt from the model solution. 2. Perform a syntax check. Why does this method call cause a syntax error? The up-cast in the parameter passing of the method does not work because the types LCL_RENTAL and LIF_PARTNER are not compatible. They will become compatible, though, as soon as LCL_RENTAL implements the interface. 3. Go to the definition part of class LCL_RENTAL and declare the implementation of interface LIF_PARTNER. a) See the source text excerpt from the model solution. 4. Provide an implementation of the method defined in the interface. a) See the source text excerpt from the model solution. 5. Activate the INCLUDE with the definition and implementation of LCL_RENTAL. Then go to the main program and perform another syntax check a) Solution - Include Program BC401_INT_S3_RENTAL *------------------------------------------------* * CLASS lcl_vehicle DEFINITION *------------------------------------------------* CLASS lcl_vehicle DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_make TYPE string, display_attributes. PRIVATE SECTION. DATA: mv_make TYPE string. ENDCLASS. "lcl_vehicle DEFINITION *------------------------------------------------* * CLASS lcl_vehicle IMPLEMENTATION *------------------------------------------------* CLASS lcl_vehicle IMPLEMENTATION. METHOD constructor. mv_make = iv_make. ENDMETHOD. "constructor METHOD display_attributes. WRITE mv_make. ENDMETHOD. "display_attributes ENDCLASS. "lcl_vehicle IMPLEMENTATION *-------------------------------------------------* * CLASS lcl_truck DEFINITION *-------------------------------------------------* CLASS lcl_truck DEFINITION INHERITING FROM lcl_vehicle. PUBLIC SECTION. METHODS: constructor

208

© Copyright . All rights reserved.

Lesson: Joining Classmodels Using Interfaces

IMPORTING iv_make TYPE string iv_cargo TYPE s_plan_car, display_attributes REDEFINITION. PRIVATE SECTION. DATA: mv_cargo TYPE s_plan_car. ENDCLASS. "lcl_truck DEFINITION *-----------------------------------------------* * CLASS lcl_truck IMPLEMENTATION *------------------------------------------------* CLASS lcl_truck IMPLEMENTATION. METHOD constructor. super->constructor( iv_make ). mv_cargo = iv_cargo. ENDMETHOD. "constructor METHOD display_attributes. WRITE / icon_ws_truck AS ICON. super->display_attributes( ). WRITE: 20 'Max. Cargo:'(005), mv_cargo. ULINE. ENDMETHOD. "display_attributes ENDCLASS. "lcl_truck DEFINITION *-------------------------------------------------* * CLASS lcl_bus DEFINITION *-------------------------------------------------* CLASS lcl_bus DEFINITION INHERITING FROM lcl_vehicle. PUBLIC SECTION. METHODS: constructor IMPORTING iv_make TYPE string iv_passengers TYPE i, display_attributes REDEFINITION. PRIVATE SECTION. DATA: mv_passengers TYPE i. ENDCLASS. "lcl_bus DEFINITION *--------------------------------------------------* * CLASS lcl_bus IMPLEMENTATION *--------------------------------------------------* CLASS lcl_bus IMPLEMENTATION. METHOD constructor. super->constructor( iv_make ). mv_passengers = iv_passengers. ENDMETHOD. "constructor METHOD display_attributes. WRITE: / icon_transportation_mode AS ICON. super->display_attributes( ). WRITE: 20 'Max. Passengers: '(006), mv_passengers. ULINE. ENDMETHOD. "display_attributes ENDCLASS. "lcl_bus DEFINITION

© Copyright . All rights reserved.

209

Unit 4: Interfaces and Casting

*-------------------------------------------------* * CLASS lcl_rental DEFINITION *-------------------------------------------------* CLASS lcl_rental DEFINITION. PUBLIC SECTION. INTERFACES: lif_partner. METHODS: constructor IMPORTING iv_name TYPE string, add_vehicle IMPORTING io_vehicle TYPE REF TO lcl_vehicle, display_attributes. PRIVATE SECTION. DATA: mv_name TYPE string, mt_vehicles TYPE TABLE OF REF TO lcl_vehicle. ENDCLASS. "lcl_rental DEFINITION *----------------------------------------------* * CLASS lcl_rental IMPLEMENTATION *----------------------------------------------* CLASS lcl_rental IMPLEMENTATION. METHOD constructor. mv_name = iv_name. ENDMETHOD. "constructor METHOD add_vehicle. APPEND io_vehicle TO mt_vehicles. ENDMETHOD. "add_vehicle METHOD display_attributes. DATA: lo_vehicle TYPE REF TO lcl_vehicle. WRITE: / icon_transport_proposal AS ICON, mv_name. ULINE. ULINE. LOOP AT mt_vehicles INTO lo_vehicle. lo_vehicle->display_attributes( ). ENDLOOP. ENDMETHOD. "display_attributes METHOD lif_partner~display_partner. me->display_attributes( ). ENDMETHOD. "lif_partner~display_partner ENDCLASS. "lcl_rental IMPLEMENTATION b) Solution - Main Program SAPBC401_INT_S3 REPORT sapbc401_int_s3. TYPE-POOLS icon. INCLUDE bc401_int_s3_agency. INCLUDE bc401_int_s3_carrier.

210

© Copyright . All rights reserved.

Lesson: Joining Classmodels Using Interfaces

INCLUDE bc401_int_s3_rental. DATA: go_vehicle TYPE REF TO lcl_vehicle, go_truck TYPE REF TO lcl_truck, go_bus TYPE REF TO lcl_bus, go_rental TYPE REF TO lcl_rental. DATA: go_agency TYPE REF TO lcl_travel_agency, go_carrier TYPE REF TO lcl_carrier, go_airplane TYPE REF TO lcl_airplane, go_cargo TYPE REF TO lcl_cargo_plane, go_passenger TYPE REF TO lcl_passenger_plane, gv_count TYPE i. START-OF-SELECTION. ******************* ******* create travel_agency CREATE OBJECT go_agency EXPORTING iv_name = 'Travel&Smile Travel'. ******* create rental CREATE OBJECT go_rental EXPORTING iv_name = 'Happy Car Rental'. ***** Insert rental company into partner list of ***** travel agency go_agency->add_partner( go_rental ). ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'MAN' iv_cargo = 45. go_rental->add_vehicle( go_truck ). ******* create truck CREATE OBJECT go_bus EXPORTING iv_make = 'Mercedes' iv_passengers = 80. go_rental->add_vehicle( go_bus ). ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'VOLVO' iv_cargo = 48. go_rental->add_vehicle( go_truck ). ***** Create Carrier

© Copyright . All rights reserved.

211

Unit 4: Interfaces and Casting

CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly-Travel'. ***** Insert carrier into business partner list ***** of travel agency go_agency->add_partner( go_carrier ). ***** Passenger Plane CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. go_carrier->add_airplane( go_passenger ). ENDIF. ***** cargo Plane CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. go_carrier->add_airplane( go_cargo ). ENDIF. ******* show attributes of all partners of travel_agency go_agency->display_attributes( ). Why does the call of ADD_PARTNER now work for the car rental company? Because now the types LCL_RENTAL and LIF_PARTNER are compatible. LCL_RENTAL implements interface LIF_PARTNER. Any instance of LCL_RENTAL is accepted as a business partner.

212

© Copyright . All rights reserved.

Lesson: Joining Classmodels Using Interfaces

Implementation of Interface Hierarchies

Figure 91: Interface Hierarchy in the Application Example

An interface implementation strongly resembles regular inheritance. You need to understand what the interface  hierarchy looks like. You need to explain interface hierarchies using an application example. In this example, you need to know whether it is useful to define a further service for “room reservation” in the interface LIF_PARTNER. In this case, the classes LCL_CARRIER and LCL_RENTAL need to implement the appropriate method because they have integrated with the interface LIF_PARTNER. However, keeping the same semantics is not conceivable for airlines or car rental companies  when we implement the  "room reservation" service. However, because there are several other business partner types for which this implementation is useful, for example, motels and hotels, the method needs to be defined centrally and not individually for motels and hotels. If we also need to  extend the model with other accommodation provider types, for example, guesthouses, then the interface hierarchy needs to be retained.

© Copyright . All rights reserved.

213

Unit 4: Interfaces and Casting

Compound Interface in Unified Modeling Language (UML) Notation

Figure 92: Compound Interface in UML Notation

In ABAP Objects, interfaces like regular superclasses can include other interfaces. As with regular inheritance, the interface hierarchies can be of any depth. The including interface is a specialization of the included interface. The including interface is known as a compound interface, represents an extension of the included interface. An included interface represents a component of another interface and is therefore known as a component interface. An interface that does not contain other interfaces in itself is known as an elementary interface. The UML notation corresponds to the implementation of an elementary interface by a class.

214

© Copyright . All rights reserved.

Lesson: Joining Classmodels Using Interfaces

Definition and Implementation of Compound Interfaces – Syntax

Figure 93: Definition and Implementation of Compound Interfaces – Syntax

As with regular inheritance, the implementing class only needs to list the compound interface in order to integrate all components. Nevertheless, the components of the component interfaces keep their original names: component_interface_name~component_name They are therefore not prefixed by the name of the compound interface. All implementations of methods from all higher level interfaces must take place in the first implementing class. Alias names are suitable for short-form syntax when accessing components from different interfaces. The implementing class provides a central view of all components with their alias names.

© Copyright . All rights reserved.

215

Unit 4: Interfaces and Casting

Addressing Components in Compound Interfaces – Syntax

Figure 94: Addressing Components in Compound Interfaces – Syntax

You need to address the components from a compound interface and do cast assignments the same way.

Correct Use of Interfaces

Figure 95: Using Interfaces

Interfaces are used to describe protocols for using components without connecting any implementation. An intermediate layer is introduced to protect the client from the explicit server, thereby making the client independent. Interfaces enable different classes to be handled uniformly, provided those classes have implemented the interfaces. As with inheritance, you can also perform polymorphism using interface reference variables.

216

© Copyright . All rights reserved.

Lesson: Joining Classmodels Using Interfaces

As is the case with regular inheritance, the definition of an interface means the abstraction of the implementing classes to a specific aspect. Multiple inheritances can be simulated using interfaces. If several interfaces are included, all components are available to each of the interfaces and you must implement all methods.

© Copyright . All rights reserved.

217

Unit 4: Interfaces and Casting

LESSON SUMMARY You should now be able to:

218



Implement down-casts with interfaces



Integrate different submodels using interfaces



Create and use interface hierarchies

© Copyright . All rights reserved.

Unit 4 Learning Assessment

1. Which of the following technically differentiates interfaces from regular inheritance? Choose the correct answer. X

A Interfaces are superclasses that can be instantiated

X

B Interfaces do not have an implementation part

X

C Interfaces have only public components

2. Which of the following is defined in the interface? Choose the correct answer. X

A Services

X

B Methods

X

C Classes

3. Which of the following statements is used to implement an interface in a class? Choose the correct answer. X

A ALIASES

X

B METHODS

X

C INTERFACES

4. You can access interface components only by using an object reference. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

219

Unit 4: Learning Assessment

5. Which of the following is used to search for the implementation of a method? Choose the correct answer. X

A The dynamic type reference variable

X

B The static type reference variable

X

C Method parameters

X

D A class

6. Which of the following is the main strength of interfaces? Choose the correct answer. X

A Events

X

B Inheritance

X

C Polymorphism

7. ?=  is the down-cast assignment operator.   Determine whether this statement is true or false. X

True

X

False

8. Which of the following implementation strongly resembles inheritance? Choose the correct answer. X

A Interface

X

B Class

X

C Method

9. Interfaces like regular superclasses can include other interfaces. Determine whether this statement is true or false.

220

X

True

X

False

© Copyright . All rights reserved.

Unit 4 Learning Assessment - Answers

1. Which of the following technically differentiates interfaces from regular inheritance? Choose the correct answer. X

A Interfaces are superclasses that can be instantiated

X

B Interfaces do not have an implementation part

X

C Interfaces have only public components

2. Which of the following is defined in the interface? Choose the correct answer. X

A Services

X

B Methods

X

C Classes

3. Which of the following statements is used to implement an interface in a class? Choose the correct answer. X

A ALIASES

X

B METHODS

X

C INTERFACES

4. You can access interface components only by using an object reference. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

221

Unit 4: Learning Assessment - Answers

5. Which of the following is used to search for the implementation of a method? Choose the correct answer. X

A The dynamic type reference variable

X

B The static type reference variable

X

C Method parameters

X

D A class

6. Which of the following is the main strength of interfaces? Choose the correct answer. X

A Events

X

B Inheritance

X

C Polymorphism

7. ?=  is the down-cast assignment operator.   Determine whether this statement is true or false. X

True

X

False

8. Which of the following implementation strongly resembles inheritance? Choose the correct answer. X

A Interface

X

B Class

X

C Method

9. Interfaces like regular superclasses can include other interfaces. Determine whether this statement is true or false.

222

X

True

X

False

© Copyright . All rights reserved.

UNIT 5

Object-Oriented Events

Lesson 1 Implementing Events in Local Classes Exercise 14: Implement Events in Local Classes

224 233

Lesson 2 Implementing Events in Local Interfaces Exercise 15: Implement Event Handling for Interfaces

246 247

UNIT OBJECTIVES ●

Implement event-controlled method calls



Trigger and handle events



Register for events



Explain visibility sections in event handling



Implement events in local interfaces

© Copyright . All rights reserved.

223

Unit 5 Lesson 1 Implementing Events in Local Classes

LESSON OVERVIEW This lesson explains the method of implementing events in local classes.  Business Example As a developer, you need to implement event-controlled behavior for your model in ABAP Objects. For this reason, you require the following knowledge: ●

An understanding of how to define and trigger events   



An understanding of how to events



An understanding of how to register events



An understanding of how to implement events in local classes

LESSON OBJECTIVES After completing this lesson, you will be able to:

224



Implement event-controlled method calls



Trigger and handle events



Register for events



Explain visibility sections in event handling

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

Event-Controlled Method Calls

Figure 96: Event-Controlled Method Calls

Besides attributes and methods, classes and their instances can also contain another type of component called events. Instance events can be triggered by the instances of the class, but static events can be triggered by the class itself. Events can also be defined as interface components. Given the right circumstances, handler methods react to the triggering of this event. This means that the runtime system may call these handler methods after the event has been triggered. In other words, the client usually does not call the handler method directly. This results in a completely different modeling concept. While you are developing the class that triggers the event, you do not need to know anything about the class that is handling it. The triggering class sends a specific message to all classes and, if required, their instances. At the time of development, type of handlers and the number of handlers which may be used are not known. Because of the definition of the handler method, the range of possible results can be narrowed down. However, the results which may occur can be determined only after the event has been triggered. An event can have exporting parameters, which means that, in contrast to the explicit method call, the calling program determines the protocol. In this application example, after an instance in the Vehicle class is created, the instance triggers the event Vehicle Created.  This event is received by several instances and is processed differently by each instance. For example, the rental car company handles the purchasing of a vehicle, while the vehicle registration office registers the purchased vehicle.  

© Copyright . All rights reserved.

225

Unit 5: Object-Oriented Events

Caution: Do not confuse this concept of events in object-oriented programming with events in the ABAP runtime system, such as LOAD-OF-PROGRAM, START-OF-SELECTION, and so on. Also, do not confuse this concept with background processing or workflow control. Event Handling in a UML Class Diagram

Figure 97: Event Handling in a UML Class Diagram

In UML class diagrams, a dotted arrow with the stereotype «handlesEventOf» points from the handling class to the triggering class. The event definition and signature only appear implicitly in the handling class within the handler method. The handler methods are separated from the other methods using the stereotype «eventHandler». To Trigger and Handle Events This procedure summarizes all of the required programming steps for event controlling: 1. Define an event in a class. The syntax for this is EVENTS eventname, CLASS-EVENTS eventname. 2. Trigger an event in a class or instance. The syntax for this is RAISE EVENT eventname. 3. Define and implement the handler method in the Handler Class. The syntax for this is [CLASS -] METHODS … FOR EVENT …. OF. 4. Register handler objects or handler class to events at runtime. The syntax for this is SET HANDLER.

226

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

Trigger and Handle Events

Figure 98: Defining and Triggering Events – Syntax

Depending on the status of your application, you may not need to program every step. The separation of cause and effect in your programming should be reflected in the way you construct complex applications. Often, the event is already triggered, and all you have to do is create another event handler. Within a class, instance events are defined using the EVENTS statement, while static events are defined using the CLASS-EVENTS statement. Events can only have exporting parameters, which must be passed by value. A class or instance can trigger an event at runtime using the RAISE EVENT statement. Both instance events and static events can be triggered in instance methods. You can trigger static events only in static methods. When an event is triggered, the handler methods that are registered to this event are called in sequence. These handler methods can trigger more events of their own.

© Copyright . All rights reserved.

227

Unit 5: Object-Oriented Events

Handling Events – Syntax

Figure 99: Handling Events – Syntax

Instance events or static methods can be defined within a class to handle events. To do so, you must specify the event using the FOR EVENT statement, and the class or interface in which the event was defined using the OF statement. If the event contains exporting parameters and you want to be able to address these syntactically, you must have specified the exporting parameters immediately after IMPORTING in the definition of the method. The handler method’s signature exporting parameters are all that are allowed to be included explicitly than the exporting parameters of the associated event. The parameters are typed by the handler method during the definition of the event. The object that triggers the event determines the protocol. In addition to the explicitly defined exporting parameters, the predefined importing parameter SENDER can always be listed. By using that parameter, you can place a reference to the eventtrigger object into the handler method. Therefore, handler methods are usually called by triggered events RAISE EVENT. However, they can also be called explicitly (CALL METHOD).

228

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

Event handler Registration

Figure 100: Event handler registration

The definition of the handler method only specifies how and to which event of which class the method will react. At runtime, it needs to be determined which possible reactions will actually take place and when each of these reactions will happen. When triggering instance events, you also have to specify which event the reaction will trigger. If instance methods are set to carry out the reaction, you also have to specify which instance(s) will perform the reaction. These specifications are collectively known as registration. Registration is always carried out using the trigger. When the event is triggered, the runtime uses the registrations of the trigger to determine which event handler methods need to be called. In this example, handler methods are defined for the event of the vehicle class, the car rental class, and the vehicle registration class. However, you can only predetermine which car rental instances and vehicle registration instances will react to which vehicle instance, and when they will do so. Registrations can also be revoked.

© Copyright . All rights reserved.

229

Unit 5: Object-Oriented Events

Registering Event Handling – Syntax

Figure 101: Registering Event Handling – Syntax

Events are registered using the SET HANDLER statement. Registration is only active at program runtime. With instance events, FOR is followed by the reference to the object that triggers the event. The addition ACTIVATION 'X' is optional during registration. To undo the registration, use ACTIVATION. You can register several methods with one SET-HANDLER statement: SET HANDLER ref_handler_1->on_eventname_1 ... ref_handler_n->on_eventname_n FOR ...  

230

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

Event Handler Tables

Figure 102: Registration/Deregistration Handler Tables

Every object or class that defines events has an internal table known as the handler table. All handler methods that are registered to the various events are listed within the handler table. For instance methods, the handler table also contains references to the registered objects.

Hint: Objects that are registered for event handling are not deleted by the garbage collector, even if there are no remaining references to them.

Note: It is possible to add or remove event handlers for a given event while an event handler for this exact event is executed. If a new event handler is registered, then this event handler is added to the end of the sequence and executed when its time comes. If an existing event handler is deregistered, then this handler is deleted immediately from the event handler method sequence.

Visibility Sections in Event Handling Events are subject to the visibility concept and can therefore be considered public, protected, or private. Event handler methods also have visibility attributes. The following visibility sections determine where the events can be handled: PUBLIC



Can be accessed anywhere

© Copyright . All rights reserved.

231

Unit 5: Object-Oriented Events



PROTECTED Can only be handled within that class or its subclasses



PRIVATE Can only be handled within its class

Visibility of the handler method is as follows: PUBLIC



Anywhere in the program ●

PROTECTED Can be handled within that class or its subclasses



PRIVATE Can only be handled within its class

Event-handler methods can only have the same or more restricted visibility than the events they refer to.

232

© Copyright . All rights reserved.

Unit 5 Exercise 14 Implement Events in Local Classes

Business Example You need to include airplane and vehicle references in the airline and the car rental company’s lists. This process is to be event-controlled. Template: SAPBC401_INT_S3 Solution: SAPBC401_EVE_S1 Task 1 Define an event for the creation of an airplane. Trigger and handle the event so that the reference to the airplane is entered into the airline’s list of airplanes. 1. Use your program ZBC401_##_MAIN (## is your two-digit group number) or copy the template program. Identify the class that is suitable for triggering the event and the class that you should use for handling the event. Use your UML diagram if necessary. 2. Define the public event AIRPLANE_CREATED in class LCL_AIRPLANE. Choose a suitable method of LCL_AIRPLANE and fire the event in its implementation. 3. In class LCL_CARRIER, define a handler method for the event that you just defined (recommended name: ON_AIRPLANE_CREATED). 4. Implement the handler method so that the new airplane is added to the airplane list of the carrier. Hint: You can do that either directly or by calling the existing method ADD_AIRPLANE. In both cases, ensure that the same airplane cannot be added to the list again. Therefore, either delete method ADD_AIRPLANE or make it private. 5. Remove all calls of ADD_AIRPLANE from your main program. 6. Register the new handler method, so that every airplane created was added into the airplane list by the airline.

© Copyright . All rights reserved.

233

Unit 5: Object-Oriented Events

Note: Although this model is unrealistic, we will use it for the time being. You can create a different rule for entering the airplane later. 7. Where could the SET HANDLER statement be executed in the example given? Could this also be done from the main program?

8. Observe the execution of the program in the ABAP Debugger. 9. What would the syntax have to be in this case?

Task 2 Define an event for the creation of a vehicle. Trigger and handle the event so that the reference to the vehicle is entered into the car rental company’s list of vehicles. 1. Remove all calls of ADD_VEHICLE from your main program. 2. Define the public event VEHICLE_CREATED in class LCL_VEHICLE and fire the event in the implementation of the constructor. 3. In class LCL_RENTAL, define and implement a handler method for the event that you just defined (recommended name: ON_VEHICLE_CREATED). 4. Register the new handler method, so that every vehicle was added into the vehicle list by the car rental company. Note: Although this model is unrealistic, we will use it for the time being. A different rule for entering the vehicles could be created later. 5. Observe the execution of the program in the ABAP Debugger.

234

© Copyright . All rights reserved.

Unit 5 Solution 14 Implement Events in Local Classes

Business Example You need to include airplane and vehicle references in the airline and the car rental company’s lists. This process is to be event-controlled. Template: SAPBC401_INT_S3 Solution: SAPBC401_EVE_S1 Task 1 Define an event for the creation of an airplane. Trigger and handle the event so that the reference to the airplane is entered into the airline’s list of airplanes. 1. Use your program ZBC401_##_MAIN (## is your two-digit group number) or copy the template program. Identify the class that is suitable for triggering the event and the class that you should use for handling the event. Use your UML diagram if necessary. a) Carry out this step in the usual manner. For more information refer to the SAP Library.   2. Define the public event AIRPLANE_CREATED in class LCL_AIRPLANE. Choose a suitable method of LCL_AIRPLANE and fire the event in its implementation. a) Refer source code extract from the model solution. 3. In class LCL_CARRIER, define a handler method for the event that you just defined (recommended name: ON_AIRPLANE_CREATED). a) Refer source code extract from the model solution. 4. Implement the handler method so that the new airplane is added to the airplane list of the carrier. Hint: You can do that either directly or by calling the existing method ADD_AIRPLANE. In both cases, ensure that the same airplane cannot be added to the list again. Therefore, either delete method ADD_AIRPLANE or make it private. a) Refer source code extract from the model solution. 5. Remove all calls of ADD_AIRPLANE from your main program. a) Refer source code extract from the model solution.

© Copyright . All rights reserved.

235

Unit 5: Object-Oriented Events

6. Register the new handler method, so that every airplane created was added into the airplane list by the airline. Note: Although this model is unrealistic, we will use it for the time being. You can create a different rule for entering the airplane later. a) Refer source code extract from the model solution. 7. Where could the SET HANDLER statement be executed in the example given? Could this also be done from the main program? Either in the constructor of LCL_CARRIER or in the main program after the creation of the LCL_CARRIER but before the creation of the first airplane. 8. Observe the execution of the program in the ABAP Debugger. a) Carry out this step in the usual manner. Additional information is available in the SAP Library. 9. What would the syntax have to be in this case? SET HANDLER go_carrier->on_airplane_created FOR ALL INSTANCES. Task 2 Define an event for the creation of a vehicle. Trigger and handle the event so that the reference to the vehicle is entered into the car rental company’s list of vehicles. 1. Remove all calls of ADD_VEHICLE from your main program. a) Refer source code extract from the model solution. 2. Define the public event VEHICLE_CREATED in class LCL_VEHICLE and fire the event in the implementation of the constructor. a) Refer source code extract from the model solution. 3. In class LCL_RENTAL, define and implement a handler method for the event that you just defined (recommended name: ON_VEHICLE_CREATED). a) Refer source code extract from the model solution. 4. Register the new handler method, so that every vehicle was added into the vehicle list by the car rental company. Note: Although this model is unrealistic, we will use it for the time being. A different rule for entering the vehicles could be created later. a) Refer source code extract from the model solution.

236

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

5. Observe the execution of the program in the ABAP Debugger. a) Carry out this step in the usual manner. Additional information about the ABAP Debugger is available in the SAP Library. Include Program BC401_EVE_S1_CARRIER *--------------------------------------------------* * CLASS lcl_airplane DEFINITION *--------------------------------------------------* CLASS lcl_airplane DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype EXCEPTIONS wrong_planetype, display_attributes. CLASS-METHODS: display_n_o_airplanes, class_constructor. EVENTS: airplane_created. PROTECTED SECTION. CONSTANTS: c_pos_1 TYPE i VALUE 30. PRIVATE SECTION. TYPES: ty_planetypes TYPE STANDARD TABLE OF saplane WITH NON-UNIQUE KEY planetype. DATA: mv_name mv_planetype mv_weight mv_tankcap

TYPE TYPE TYPE TYPE

string, saplane-planetype, saplane-weight, saplane-tankcap.

CLASS-DATA: gv_n_o_airplanes TYPE i, gt_planetypes TYPE ty_planetypes. CLASS-METHODS: get_technical_attributes IMPORTING iv_type TYPE saplane-planetype EXPORTING ev_weight TYPE saplane-weight ev_tankcap TYPE saplane-tankcap

© Copyright . All rights reserved.

237

Unit 5: Object-Oriented Events

EXCEPTIONS wrong_planetype. ENDCLASS.

"lcl_airplane DEFINITION

*-------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *-------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. METHOD class_constructor. SELECT * FROM saplane INTO TABLE gt_planetypes. ENDMETHOD. "class_constructor METHOD constructor. mv_name = iv_name. mv_planetype = iv_planetype. get_technical_attributes( EXPORTING iv_type = iv_planetype IMPORTING ev_weight = mv_weight ev_tankcap = mv_tankcap EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ELSE. gv_n_o_airplanes = gv_n_o_airplanes + 1. RAISE EVENT airplane_created. ENDIF. ENDMETHOD.

"constructor

METHOD display_attributes. ... ENDMETHOD.

"display_attributes

METHOD display_n_o_airplanes. ... ENDMETHOD.

"display_n_o_airplanes

METHOD get_technical_attributes. ... ENDMETHOD. ENDCLASS.

"get_technical_attributes "lcl_airplane IMPLEMENTATION

*-------------------------------------------* * CLASS lcl_cargo_plane DEFINITION

238

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

*-------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS.

"lcl_cargo_plane DEFINITION

*-----------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *-----------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. ... ENDCLASS.

"lcl_cargo_plane IMPLEMENTATION

*------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS.

"lcl_passenger_plane DEFINITION

*-------------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *-------------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. ... ENDCLASS.

"lcl_passenger_plane IMPLEMENTATION

*--------------------------------------------------* * CLASS lcl_carrier DEFINITION *--------------------------------------------------* CLASS lcl_carrier DEFINITION. PUBLIC SECTION. INTERFACES lif_partner. METHODS: constructor IMPORTING iv_name TYPE string, display_attributes. PRIVATE SECTION. DATA: mv_name TYPE string, mt_airplanes TYPE TABLE OF REF TO lcl_airplane. METHODS: on_airplane_created FOR EVENT airplane_created

© Copyright . All rights reserved.

239

Unit 5: Object-Oriented Events

OF lcl_airplane IMPORTING sender, display_airplanes. ENDCLASS.

"lcl_carrier DEFINITION

*--------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *--------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. METHOD constructor. mv_name = iv_name. SET HANDLER on_airplane_created FOR ALL INSTANCES. ENDMETHOD. "constructor METHOD lif_partner~display_partner. display_attributes( ). ENDMETHOD. "lif_partners~display_partner METHOD on_airplane_created. APPEND sender TO mt_airplanes. ENDMETHOD. "on_airplane_created METHOD display_attributes. SKIP 2. WRITE: icon_flight AS ICON, mv_name. ULINE. ULINE. display_airplanes( ). ENDMETHOD. "display_attributes METHOD display_airplanes. DATA: lo_plane TYPE REF TO lcl_airplane. LOOP AT mt_airplanes INTO lo_plane. lo_plane->display_attributes( ). ENDLOOP. ENDMETHOD. "display_airplanes ENDCLASS.

"lcl_carrier IMPLEMENTATION Include Program BC401_EVE_S1_RENTAL

*-----------------------------------------------* * CLASS lcl_vehicle DEFINITION *-----------------------------------------------* CLASS lcl_vehicle DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_make TYPE string, display_attributes. CLASS-METHODS: get_count EXPORTING ev_count TYPE i. EVENTS: vehicle_created.

240

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

PRIVATE SECTION. DATA: mv_make TYPE string. CLASS-DATA: gv_n_o_vehicles TYPE i. ENDCLASS.

"lcl_vehicle DEFINITION

*-------------------------------------------------* * CLASS lcl_vehicle IMPLEMENTATION *-------------------------------------------------* CLASS lcl_vehicle IMPLEMENTATION. METHOD constructor. mv_make = iv_make. ADD 1 TO gv_n_o_vehicles. RAISE EVENT vehicle_created. ENDMETHOD. "constructor METHOD display_attributes. WRITE mv_make. ENDMETHOD. "display_attributes METHOD get_count. ev_count = gv_n_o_vehicles. ENDMETHOD. "get_count ENDCLASS.

"lcl_vehicle IMPLEMENTATION

*-----------------------------------------------* * CLASS lcl_truck DEFINITION *-----------------------------------------------* CLASS lcl_truck DEFINITION INHERITING FROM lcl_vehicle. ... ENDCLASS.

"lcl_truck DEFINITION

*-----------------------------------------------* * CLASS lcl_truck IMPLEMENTATION *-----------------------------------------------* CLASS lcl_truck IMPLEMENTATION. ... ENDCLASS.

"lcl_truck DEFINITION

*-------------------------------------------------* * CLASS lcl_bus DEFINITION *-------------------------------------------------* CLASS lcl_bus DEFINITION INHERITING FROM lcl_vehicle. ... ENDCLASS.

"lcl_bus DEFINITION

© Copyright . All rights reserved.

241

Unit 5: Object-Oriented Events

*-------------------------------------------------* * CLASS lcl_bus IMPLEMENTATION *-------------------------------------------------* CLASS lcl_bus IMPLEMENTATION. ... ENDCLASS.

"lcl_bus DEFINITION

*-------------------------------------------------* * CLASS lcl_rental DEFINITION *--------------------------------------------------* CLASS lcl_rental DEFINITION. PUBLIC SECTION. INTERFACES: lif_partner. METHODS: constructor IMPORTING iv_name TYPE string, display_attributes. PRIVATE SECTION. DATA: mv_name TYPE string, mt_vehicles TYPE TABLE OF REF TO lcl_vehicle. METHODS: on_vehicle_created FOR EVENT vehicle_created OF lcl_vehicle IMPORTING sender. ENDCLASS.

"lcl_rental DEFINITION

*-------------------------------------------------* * CLASS lcl_rental IMPLEMENTATION *-------------------------------------------------* CLASS lcl_rental IMPLEMENTATION. METHOD lif_partner~display_partner. display_attributes( ). ENDMETHOD. "lif_partners~display_partner METHOD constructor. mv_name = iv_name. SET HANDLER on_vehicle_created FOR ALL INSTANCES. ENDMETHOD. "constructor METHOD on_vehicle_created. APPEND sender TO mt_vehicles. ENDMETHOD. "on_vehicle_created METHOD display_attributes. DATA: lo_vehicle TYPE REF TO lcl_vehicle. WRITE: / icon_transport_proposal AS ICON,

242

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

WRITE: ULINE. ULINE.

mv_name. / 'Here comes the vehicle list: '.

LOOP AT mt_vehicles INTO lo_vehicle. lo_vehicle->display_attributes( ). ENDLOOP. ENDMETHOD. "display_attributes ENDCLASS.

"lcl_rental IMPLEMENTATION Main Program SAPBC401_EVE_S1

REPORT

sapbc401_eve_s1.

TYPE-POOLS icon. INCLUDE bc401_eve_s1_agency. INCLUDE bc401_eve_s1_carrier. INCLUDE bc401_eve_s1_rental. DATA: go_vehicle go_truck go_bus go_rental go_agency go_carrier go_airplane go_cargo go_passenger gv_count

TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE

REF REF REF REF REF REF REF REF REF i.

TO TO TO TO TO TO TO TO TO

lcl_vehicle, lcl_truck, lcl_bus, lcl_rental, lcl_travel_agency, lcl_carrier, lcl_airplane, lcl_cargo_plane, lcl_passenger_plane,

START-OF-SELECTION. ******************* ******* create travel_agency CREATE OBJECT go_agency EXPORTING iv_name = 'Travel&smile Travel'. ******* create rental CREATE OBJECT go_rental EXPORTING iv_name = 'Happy Car Rental'. ***** Insert rental company into partner list ***** of travel agency go_agency->add_partner( go_rental ). ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'MAN' iv_cargo = 45. * go_rental->add_vehicle( go_truck ).

© Copyright . All rights reserved.

243

Unit 5: Object-Oriented Events

******* create truck CREATE OBJECT go_bus EXPORTING iv_make = 'Mercedes' iv_passengers = 80. * go_rental->add_vehicle( go_bus ). ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'VOLVO' iv_cargo = 48. * go_rental->add_vehicle( go_truck ). ***** Create Carrier CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly-Travel'. ***** Insert carrier into business partner list ***** of travel agency go_agency->add_partner( go_carrier ). ***** Passenger Plane CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. *

IF sy-subrc = 0. go_carrier->add_airplane( go_passenger ). ELSE. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF.

***** cargo Plane CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc = 0. * go_carrier->add_airplane( go_cargo ). ELSE. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ***** show attributes of all partners travel agency go_agency->display_attributes( ).

244

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Classes

LESSON SUMMARY You should now be able to: ●

Implement event-controlled method calls



Trigger and handle events



Register for events



Explain visibility sections in event handling

© Copyright . All rights reserved.

245

Unit 5 Lesson 2 Implementing Events in Local Interfaces

LESSON OVERVIEW This lesson explains the implementation of events in local interfaces. Business Example As a developer, you need to implement events in local classes of the airplane. For this reason, you require the following knowledge: ●

An understanding of events



An understanding of interfaces



An understanding of implementing events in local interfaces

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Implement events in local interfaces

Implement Event in a Local Interface Events can be defined as interface components. Triggering and handling events are done the same way as in classes. Steps to implement event handling for Interfaces are as follows: 1. Define events in interfaces 2. Trigger interface events in implementing classes 3. Handle interface events 4. Register event handling

246

© Copyright . All rights reserved.

Unit 5 Exercise 15 Implement Event Handling for Interfaces

Business Example Airline and car rental company references are to be entered into the travel agent’s list. This process is to be event-controlled. Be sure to create your program so that it can be easily extended to manage additional business partners of the travel agent in the future. Template: SAPBC401_EVE_S1 Solution: SAPBC401_EVE_S2 Define an event for the creation of a business partner. Trigger and handle the event so that the reference to the business partner is entered into the travel agent’s list of partners. 1. Use your ZBC401_##_MAIN program or copy the model solution from the previous exercise (where ## is your two-digit group number). 2. Remove the calls of the method ADD_PARTNER from your main program. Note: The entry of a business partner reference into the travel agent’s list is to be eventcontrolled. 3. If necessary, examine your UML diagram. Which class or interface should define the event? Which class or interface should trigger it? Which class or interface should handle it? If applicable, illustrate the relationships in your UML diagram. 4. Define the event PARTNER_CREATED and trigger it using a suitable method in all classes that implement the interface. 5. Remove the method ADD_PARTNER in the class LCL_TRAVEL_AGENCY. Replace it by a handler method for the event that you just defined (suggested name: ON_PARTNER_CREATED). 6. Register the new handler method, so that every business partner created was added into the partner list by the travel agency.

© Copyright . All rights reserved.

247

Unit 5: Object-Oriented Events

Note: Although this model is unrealistic, we will use it for the time being. A different rule for entering the business partner can be created later. 7. Observe the execution of the program in the ABAP Debugger.

248

© Copyright . All rights reserved.

Unit 5 Solution 15 Implement Event Handling for Interfaces

Business Example Airline and car rental company references are to be entered into the travel agent’s list. This process is to be event-controlled. Be sure to create your program so that it can be easily extended to manage additional business partners of the travel agent in the future. Template: SAPBC401_EVE_S1 Solution: SAPBC401_EVE_S2 Define an event for the creation of a business partner. Trigger and handle the event so that the reference to the business partner is entered into the travel agent’s list of partners. 1. Use your ZBC401_##_MAIN program or copy the model solution from the previous exercise (where ## is your two-digit group number). a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 2. Remove the calls of the method ADD_PARTNER from your main program. Note: The entry of a business partner reference into the travel agent’s list is to be eventcontrolled. a) See the source code extract from the model solution. 3. If necessary, examine your UML diagram. Which class or interface should define the event? Which class or interface should trigger it? Which class or interface should handle it? If applicable, illustrate the relationships in your UML diagram. a) Speak to your instructor if you have any questions. 4. Define the event PARTNER_CREATED and trigger it using a suitable method in all classes that implement the interface. a) See the source code extract from the model solution. 5. Remove the method ADD_PARTNER in the class LCL_TRAVEL_AGENCY. Replace it by a handler method for the event that you just defined (suggested name: ON_PARTNER_CREATED). a) See the source code extract from the model solution.

© Copyright . All rights reserved.

249

Unit 5: Object-Oriented Events

6. Register the new handler method, so that every business partner created was added into the partner list by the travel agency. Note: Although this model is unrealistic, we will use it for the time being. A different rule for entering the business partner can be created later. a) Refer the source code extract from the model solution. 7. Observe the execution of the program in the ABAP Debugger. a) Carry out this step in the usual manner. Additional information about the ABAP Debugger is available in the SAP Library. Solution - Include Program BC401_EVE_S2_AGENCY *-----------------------------------------------* * INTERFACE lif_partners *&----------------------------------------------* INTERFACE lif_partner. METHODS: display_partner. EVENTS: partner_created. ENDINTERFACE. "lif_partners *------------------------------------------------* * CLASS lcl_travel_agency DEFINITION *------------------------------------------------* CLASS lcl_travel_agency DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string, display_agency_partners, display_attributes. PRIVATE SECTION. DATA: mv_name TYPE string, mt_partners TYPE TABLE OF REF TO lif_partner. METHODS: on_partner_created FOR EVENT partner_created OF lif_partner IMPORTING sender. ENDCLASS. "lcl_travel_agency DEFINITION *-------------------------------------------------* * CLASS lcl_travel_agency IMPLEMENTATION *-------------------------------------------------* CLASS lcl_travel_agency IMPLEMENTATION. METHOD display_attributes. WRITE: / icon_private_files AS ICON, 'Travel Agency:'(007), mv_name. SKIP.

250

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Interfaces

display_agency_partners( ). ENDMETHOD.

"display_attributes

METHOD display_agency_partners. DATA: lo_partner TYPE REF TO lif_partner. WRITE 'Here are the partners of the travel agency:'(008). ULINE. LOOP AT mt_partners INTO lo_partner. lo_partner->display_partner( ). ENDLOOP. ENDMETHOD.

"display_agency_partners

METHOD constructor. mv_name = iv_name. SET HANDLER on_partner_created FOR ALL INSTANCES. ENDMETHOD. "constructor METHOD on_partner_created. APPEND sender TO mt_partners. ENDMETHOD. "on_partner_created ENDCLASS.

"lcl_travel_agency IMPLEMENTATION Solution - Include Program BC401_EVE_S2_RENTAL

*--------------------------------------------------* * CLASS lcl_vehicle DEFINITION *--------------------------------------------------* CLASS lcl_vehicle DEFINITION. ... ENDCLASS. "lcl_vehicle DEFINITION *--------------------------------------------------* * CLASS lcl_vehicle IMPLEMENTATION *--------------------------------------------------* CLASS lcl_vehicle IMPLEMENTATION. ... ENDCLASS. "lcl_vehicle IMPLEMENTATION *--------------------------------------------------* * CLASS lcl_truck DEFINITION *--------------------------------------------------* CLASS lcl_truck DEFINITION INHERITING FROM lcl_vehicle. ... ENDCLASS. "lcl_truck DEFINITION *--------------------------------------------------* * CLASS lcl_truck IMPLEMENTATION *--------------------------------------------------* CLASS lcl_truck IMPLEMENTATION. ... ENDCLASS. "lcl_truck DEFINITION

© Copyright . All rights reserved.

251

Unit 5: Object-Oriented Events

*--------------------------------------------------* * CLASS lcl_bus DEFINITION *--------------------------------------------------* CLASS lcl_bus DEFINITION INHERITING FROM lcl_vehicle. ... ENDCLASS. "lcl_bus DEFINITION *--------------------------------------------------* * CLASS lcl_bus IMPLEMENTATION *--------------------------------------------------* CLASS lcl_bus IMPLEMENTATION. ... ENDCLASS. "lcl_bus DEFINITION *--------------------------------------------------* * CLASS lcl_rental DEFINITION *--------------------------------------------------* CLASS lcl_rental DEFINITION. ... ENDCLASS. "lcl_rental DEFINITION *--------------------------------------------------* * CLASS lcl_rental IMPLEMENTATION *--------------------------------------------------* CLASS lcl_rental IMPLEMENTATION. METHOD lif_partner~display_partner. display_attributes( ). ENDMETHOD. "lif_partners~display_partner METHOD constructor. mv_name = iv_name. SET HANDLER on_vehicle_created FOR ALL INSTANCES. RAISE EVENT lif_partner~partner_created. ENDMETHOD.

"constructor

METHOD on_vehicle_created. APPEND sender TO mt_vehicles. ENDMETHOD. "on_vehicle_created METHOD display_attributes. ... ENDMETHOD. "display_attributes ENDCLASS.

"lcl_rental IMPLEMENTATION Solution - Include Program BC401_EVE_S2_CARRIER

*-------------------------------------------------* * CLASS lcl_airplane DEFINITION *-------------------------------------------------*

252

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Interfaces

CLASS lcl_airplane DEFINITION. ... ENDCLASS. "lcl_airplane DEFINITION *-------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *-------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. ... ENDCLASS. "lcl_airplane IMPLEMENTATION *-------------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *-------------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS. "lcl_cargo_plane DEFINITION *-------------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *-------------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. ... ENDCLASS. "lcl_cargo_plane IMPLEMENTATION *-------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *-------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane. ... ENDCLASS. "lcl_passenger_plane DEFINITION *-------------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *-------------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. ... ENDCLASS. "lcl_passenger_plane IMPLEMENTATION *-------------------------------------------------* * CLASS lcl_carrier DEFINITION *-------------------------------------------------* CLASS lcl_carrier DEFINITION. ... ENDCLASS. "lcl_carrier DEFINITION *-------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *-------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. METHOD constructor. mv_name = iv_name. SET HANDLER on_airplane_created FOR ALL INSTANCES. RAISE EVENT lif_partner~partner_created. ENDMETHOD. "constructor

© Copyright . All rights reserved.

253

Unit 5: Object-Oriented Events

METHOD lif_partner~display_partner. display_attributes( ). ENDMETHOD. "lif_partners~display_partner METHOD on_airplane_created. APPEND sender TO mt_airplanes. ENDMETHOD. "on_airplane_created METHOD display_attributes. ... ENDMETHOD. "display_attributes METHOD display_airplanes. ... ENDMETHOD. "display_airplanes ENDCLASS.

"lcl_carrier IMPLEMENTATION

Solution - Main Program SAPBC401_EVE_S2 REPORT sapbc401_eve_s2. TYPE-POOLS icon. INCLUDE bc401_eve_s2_agency. INCLUDE bc401_eve_s2_carrier. INCLUDE bc401_eve_s2_rental. DATA: go_vehicle TYPE REF TO lcl_vehicle, go_truck TYPE REF TO lcl_truck, go_bus TYPE REF TO lcl_bus, go_rental TYPE REF TO lcl_rental, go_passenger TYPE REF TO lcl_passenger_plane, go_cargo TYPE REF TO lcl_cargo_plane, go_carrier TYPE REF TO lcl_carrier, go_agency TYPE REF TO lcl_travel_agency. START-OF-SELECTION. ******************* ******* create travel_agency CREATE OBJECT go_agency EXPORTING iv_name = 'Travel&Smile Travel'. ******* create rental CREATE OBJECT go_rental EXPORTING iv_name = 'Happy Car Rental'. * go_agency->add_partner( go_rental ). ******* create truck CREATE OBJECT go_truck EXPORTING

254

© Copyright . All rights reserved.

Lesson: Implementing Events in Local Interfaces

iv_make = 'MAN' iv_cargo = 45. ******* create truck CREATE OBJECT go_bus EXPORTING iv_name = 'Mercedes' iv_passengers = 80. ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'VOLVO' iv_cargo = 48. ***** Create Carrier CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly-Travel'. * go_agency->add_partner( go_rental ). ***** Passenger Plane CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ***** cargo Plane CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ******* show attributes of all partners of travel_agency go_agency->display_attributes( ).

© Copyright . All rights reserved.

255

Unit 5: Object-Oriented Events

LESSON SUMMARY You should now be able to: ●

256

Implement events in local interfaces

© Copyright . All rights reserved.

Unit 5 Learning Assessment

1. Which of the following are not defined as interface components?  Choose the correct answer. X

A Attributes

X

B Methods

X

C Events

X

D Classes

2. Which of the following statements is used to define events within a class?  Choose the correct answer. X

A CLASS-EVENTS

X

B RAISE EVENT

X

C EVENTS

X

D FOR EVENTS

3. Which of the following statements is used to trigger events?  Choose the correct answer. X

A CLASS-EVENTS

X

B RAISE EVENT

X

C EVENTS

X

D FOR EVENTS

© Copyright . All rights reserved.

257

Unit 5: Learning Assessment

4. You can trigger static events only in static methods. Determine whether this statement is true or false. X

True

X

False

5. Which of the following is specified by the definition of the handler method?  Choose the correct answer. X

A which method will react to which event of which class

X

B which event the reaction will trigger

X

C which instance(s) will perform the reaction

6. Events are registered using the SET HANDLER statement. Registration is only active at program runtime. Determine whether this statement is true or false. X

True

X

False

7. Every object or class that has a defined event does not have a handler table. Determine whether this statement is true or false. X

True

X

False

8. Which of the following is used to handle the visibility of the event within the class or its subclasses? Choose the correct answer.

258

X

A Public

X

B Protected

X

C Private

© Copyright . All rights reserved.

Unit 5 Learning Assessment - Answers

1. Which of the following are not defined as interface components?  Choose the correct answer. X

A Attributes

X

B Methods

X

C Events

X

D Classes

2. Which of the following statements is used to define events within a class?  Choose the correct answer. X

A CLASS-EVENTS

X

B RAISE EVENT

X

C EVENTS

X

D FOR EVENTS

3. Which of the following statements is used to trigger events?  Choose the correct answer. X

A CLASS-EVENTS

X

B RAISE EVENT

X

C EVENTS

X

D FOR EVENTS

© Copyright . All rights reserved.

259

Unit 5: Learning Assessment - Answers

4. You can trigger static events only in static methods. Determine whether this statement is true or false. X

True

X

False

5. Which of the following is specified by the definition of the handler method?  Choose the correct answer. X

A which method will react to which event of which class

X

B which event the reaction will trigger

X

C which instance(s) will perform the reaction

6. Events are registered using the SET HANDLER statement. Registration is only active at program runtime. Determine whether this statement is true or false. X

True

X

False

7. Every object or class that has a defined event does not have a handler table. Determine whether this statement is true or false. X

True

X

False

8. Which of the following is used to handle the visibility of the event within the class or its subclasses? Choose the correct answer.

260

X

A Public

X

B Protected

X

C Private

© Copyright . All rights reserved.

UNIT 6

Object-Oriented Repository Objects

Lesson 1 Creating Global Classes Exercise 16: Implement a Global Class

262 273

Lesson 2 Defining and Implementing Global Interfaces Exercise 17: Import and Implement a Global Interface

280 285

Lesson 3 Implementing Inheritance in Global Classes Exercise 18: Implement Inheritance in Global Classes

294 301

UNIT OBJECTIVES ●

Create global classes



Test global classes



Use global classes



Define and implement global interfaces



Import local classes and interfaces



Generate UML diagrams for global classes



Implement inheritance in global classes



Handle global classes



Use the Refactoring Assistant

© Copyright . All rights reserved.

261

Unit 6 Lesson 1 Creating Global Classes

LESSON OVERVIEW This lesson explains the method of creating global classes. Business Example As a developer, you must create a global ABAP class for an airplane class that can be accessed by all other ABAP Objects in the SAP system. For this reason, you require the following knowledge: ●

An understanding of global classes



An understanding of how to test and use global classes

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Create global classes



Test global classes



Use global classes

Definition of Global Classes Note: A large number of screenshots and screen illustrations are used in the lesson. Note that the appearance of some of the icons or menus depends on the release level. As with subroutines, use local classes or interfaces only within the program in which they are defined and implemented. The CLASS statement is a local declarative statement in the program. As the TYPES statement defines local data types, the CLASS statement defines local object types. On the other hand, global classes or global interfaces are individual repository objects with all the standard ABAP Workbench features such as active integration, versioning, transport system, and so on. The namespace convention, for example Y*, Z*, or a special customer namespace is the same as that name used for the namespace of other repository objects. Therefore, a special maintenance tool is available in the ABAP Workbench, that is the Class Builder. In case you are unsure about a certain feature in the Class Builder, you are advised to use the Quickinfo. It is the explanatory text that appears when you place the cursor over an icon and leave it there for a short time.

262

© Copyright . All rights reserved.

Lesson: Creating Global Classes

Creating Global Classes in the Object Navigator

Figure 103: Creating Global Classes in the Object Navigator

As with other repository objects, the separate navigation area of the Object Navigator makes it the ideal development tool for all repository objects. The easiest way to create a new global class is to use the context menu in the navigation area. To do so, first select the package node or select the class node within a package. A dialog box appears that offers you some choices for the new class. Select usual ABAP class. The global class or global interface is then displayed in the Class Builder table in the editor area of the Object Navigator.

© Copyright . All rights reserved.

263

Unit 6: Object-Oriented Repository Objects

Definition of Attributes in a Global Class

Figure 104: Definition of Attributes

Choose the Attributes tab page to open a list of all attribute definitions in the class. You can also define new attributes here. You can use the input help when defining the types of attributes. Remember to use meaningful short descriptions.

264

© Copyright . All rights reserved.

Lesson: Creating Global Classes

Create Methods in Global Class

Figure 105: Definition of Methods

Choose the Methods tab page to open a list of all method definitions in the class. You can define new methods here. Remember to use meaningful short descriptions. There are separate editor windows for the method parameters (also known as method signature) and the implementation. Choose the Constructor pushbutton to define an instance constructor. The system automatically chooses the name of constructor.

Hint: Methods can be transported separately because each implementation is stored in an own ABAP include.

© Copyright . All rights reserved.

265

Unit 6: Object-Oriented Repository Objects

Definition of Method Parameters

Figure 106: Definition of Method Signatures

In the method list, select a method and choose the Parameter pushbutton to go to the signature maintenance. You can define new formal parameters here. You can use the input help when defining the type of the parameters. Remember to use meaningful short descriptions. You can browse between the signatures with the help of the Previous Method or Next Methods pushbutton. Choose the Methods pushbutton to return to the method list. Implementation of Methods

Figure 107: Implementation of Methods

266

© Copyright . All rights reserved.

Lesson: Creating Global Classes

In the method list, select a method by double-clicking it. Alternatively, choose the Source code pushbutton to go to the source text maintenance if a method is already selected. You can implement the methods here.

Hint: Choose the relevant pushbutton to display the method’s signature.

Displaying the Method Definition

Figure 108: Displaying the Method Definition

Choose Goto → Method definition to change the attributes of your method during implementation. Optionally, you can define an event handler method on the Attributes tab page in the dialog box.

© Copyright . All rights reserved.

267

Unit 6: Object-Oriented Repository Objects

Definition of Components Using the Navigation Area

Figure 109: Definition of Components Using the Navigation Area

You can  define attributes, methods, or events in the context menu of the Object Navigator’s navigation area. The properties are then maintained in a dialog box, and not in the table.

Hint: Choose Class → Print or Method → Print to print selected portions of the source text.

268

© Copyright . All rights reserved.

Lesson: Creating Global Classes

Class Builder Testing Environment

Figure 110: The Class Builder Testing Environment

You can test active active global classes by choosing menu path Class → Run → In Test Environment, click the corresponding toolbar button, or press F8. Static attributes and static methods are directly accessible in the test environment. Instance attributes and instance methods are accessible after instance creation only. You can create an instance using the Create Instance pushbutton. The system only lists the public components. Methods can be tested using the Execute Method icon. Following are the steps to trigger events in a class: 1. Select an event. 2. Choose Handler to register a standard method for the event. 3. Call a method in which the event trigger was implemented. The event that was triggered and all of the exported actual parameters are displayed in a list.

© Copyright . All rights reserved.

269

Unit 6: Object-Oriented Repository Objects

Usage of Global Classes in the ABAP Editor

Figure 111: Separation of Navigation and Editing Areas in the Object Navigator

Like other repository objects, global classes and interfaces are added in the navigation area of the object navigator. This way, the discussed advantages also apply to global classes and interfaces. Object Instantiation Using Drag and Drop

Figure 112: Object Instantiation Using Drag and Drop

270

© Copyright . All rights reserved.

Lesson: Creating Global Classes

In the navigation area, select a class name and drag it to the editing area by holding down the left mouse pushbutton. This action creates a CREATE OBJECT statement. Then, add the reference variable and the actual parameters, if applicable, to the statement. Alternatively, you can also choose the Pattern pushbutton. You can find the CREATE OBJECT statement by selecting ABAP Objects Patterns. You can generate the statement using the input help. Your demonstration program will look similar to program SAPBC401_GCL_D1. It is recommended that you let the participants perform  the first exercise of this lesson. Method Calls Using Drag and Drop

Figure 113: Method Calls Using Drag and Drop

In the navigation area, select a method name and drag it to the editing area by holding down the left mouse pushbutton. This action creates a CREATE METHOD statement. Then, add the reference variable and the actual parameters, if applicable, to the statement. Alternatively, you can also choose the Pattern pushbutton. The CALL METHOD statement is under ABAP Objects Pattern. You can generate the statement using the input help.

Note: To generate patterns, you can, as of SAP Netweaver 7.0, enable the modern functional writing style for method calls. Choose Utilities → Settings → Pattern and select the Functional Writing Style for Call Method checkbox.

© Copyright . All rights reserved.

271

Unit 6: Object-Oriented Repository Objects

272

© Copyright . All rights reserved.

Unit 6 Exercise 16 Implement a Global Class

Business Example You want to create a global class to represent hotels. Template: SAPBC401_EVE_S2 (main program) Solution: SAPBC401_GCL_S1 (main program) CL_HOTEL (global class) Task 1 Create a global class for hotels 1. Create the global class ZCL_##_HOTEL (## is your two-digit group number). 2. Define the following attributes in the class: Attribute Name

Type

Characteristics

C_POS_1

I

As a private constant with value 30.

MV_NAME

of the type STRING

As a private instance attribute.

MV_BEDS

of the type I

As a private instance attribute.

GV_N_O_HOTELS

of the type I

As a private static attribute.

Maintain the short texts. 3. Define the following methods in the class: Method Name

Method Characteristics

CONSTRUCTOR

Instance constructor for setting the private attributes with the import parameters IM_NAME and IM_BEDS

DISPLAY_ATTRIBUTES

Instance method for displaying attributes in an ABAP list

© Copyright . All rights reserved.

273

Unit 6: Object-Oriented Repository Objects

Method Name

Method Characteristics

DISPLAY_N_O_HOTELS

Static method to display the number of created hotel instances in an ABAP list

4. Use the constant defined before to align the output of the values in a column. Maintain the short texts.

Task 2 Check your work. 1. Activate your class. 2. Test your class in the Class Builder’s testing environment. Task 3 Create an instance of your global class for hotels in your main program. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the template program. 2. Define a reference variable, specify your global hotel class as the type, and create an instance. 3. If you have not done the optional exercise, where you add business partners to the travel agency through event handling, call method ADD_PARTNER for the hotel. 4. Why can the hotel not yet be integrated into the list of travel agency of business partners?

5. Could the local interface LIF_PARTNER be implemented in the global class for hotels?

274

© Copyright . All rights reserved.

Unit 6 Solution 16 Implement a Global Class

Business Example You want to create a global class to represent hotels. Template: SAPBC401_EVE_S2 (main program) Solution: SAPBC401_GCL_S1 (main program) CL_HOTEL (global class) Task 1 Create a global class for hotels 1. Create the global class ZCL_##_HOTEL (## is your two-digit group number). a) Follow the processes as outlined in the relevant section of this lesson. 2. Define the following attributes in the class: Attribute Name

Type

Characteristics

C_POS_1

I

As a private constant with value 30.

MV_NAME

of the type STRING

As a private instance attribute.

MV_BEDS

of the type I

As a private instance attribute.

GV_N_O_HOTELS

of the type I

As a private static attribute.

Maintain the short texts. a) Follow the processes as outlined in the relevant section of this lesson. 3. Define the following methods in the class: Method Name

Method Characteristics

CONSTRUCTOR

Instance constructor for setting the private attributes with the import parameters IM_NAME and IM_BEDS

© Copyright . All rights reserved.

275

Unit 6: Object-Oriented Repository Objects

Method Name

Method Characteristics

DISPLAY_ATTRIBUTES

Instance method for displaying attributes in an ABAP list

DISPLAY_N_O_HOTELS

Static method to display the number of created hotel instances in an ABAP list

4. Use the constant defined before to align the output of the values in a column. Maintain the short texts. a) Follow the processes as outlined in the relevant section of this lesson.

Task 2 Check your work. 1. Activate your class. a) Carry out this step in the usual manner. Additional information is available in the SAP Library. 2. Test your class in the Class Builder’s testing environment. a) Follow the processes as outlined in the relevant section of this lesson. Task 3 Create an instance of your global class for hotels in your main program. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the template program. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 2. Define a reference variable, specify your global hotel class as the type, and create an instance. a) See source text excerpt from the model solution. 3. If you have not done the optional exercise, where you add business partners to the travel agency through event handling, call method ADD_PARTNER for the hotel. a) Perform in the same way as for the carrier and the car rental company. 4. Why can the hotel not yet be integrated into the list of travel agency of business partners? The global class for hotels does not implement the interface that is used by the travel agency class. 5.

276

© Copyright . All rights reserved.

Lesson: Creating Global Classes

Could the local interface LIF_PARTNER be implemented in the global class for hotels? No, global classes can only implement global interfaces. Therefore, the local interface must be replaced with a global one. This is performed in the next exercise. a) Model solution as follows. Solution - Main Program SAPBC401_GCL_S1 REPORT

sapbc401_gcl_s1.

TYPE-POOLS icon. INCLUDE bc401_gcl_s1_agency. INCLUDE bc401_gcl_s1_carrier. INCLUDE bc401_gcl_s1_rental. DATA: go_hotel go_vehicle go_truck go_bus go_rental go_passenger go_cargo go_carrier go_agency

TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE

REF REF REF REF REF REF REF REF REF

TO TO TO TO TO TO TO TO TO

cl_hotel, lcl_vehicle, lcl_truck, lcl_bus, lcl_rental, lcl_passenger_plane, lcl_cargo_plane, lcl_carrier, lcl_travel_agency.

START-OF-SELECTION. ******************* ******* create travel_agency CREATE OBJECT go_agency EXPORTING iv_name = 'Travel&Smile Travel'. ******* create hotel CREATE OBJECT go_hotel EXPORTING iv_name = 'Sleep Well Hotel' iv_beds = 345. * hotel not added to partner list * does not implement interface * go_agency->add_partner( go_hotel ) ******* create rental CREATE OBJECT go_rental EXPORTING iv_name = 'Happy Car Rental'. * go_agency->add_partner( go_rental ). ******* create truck CREATE OBJECT go_truck EXPORTING

© Copyright . All rights reserved.

277

Unit 6: Object-Oriented Repository Objects

iv_make = 'MAN' iv_cargo = 45. ******* create truck CREATE OBJECT go_bus EXPORTING iv_make = 'Mercedes' iv_passengers = 80. ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'VOLVO' iv_cargo = 48. ***** Create Carrier CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly-Travel'. * go_agency->add_partner( go_rental ). ***** Passenger Plane CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ***** cargo Plane CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ***** show attributes of all partners of travel_agency go_agency->display_attributes( ).

278

© Copyright . All rights reserved.

Lesson: Creating Global Classes

LESSON SUMMARY You should now be able to: ●

Create global classes



Test global classes



Use global classes

© Copyright . All rights reserved.

279

Unit 6 Lesson 2 Defining and Implementing Global Interfaces

LESSON OVERVIEW This lesson explains how to define and implement global interfaces. Business Example As a developer, you need to create a global interface so that other developers in your organization can use the same interface and implement it in their own ways in their classes. For this reason, you require the following knowledge: ●

An understanding of how to define and implement global interfaces



An understanding of how to import local classes and interfaces

LESSON OBJECTIVES After completing this lesson, you will be able to:

280



Define and implement global interfaces



Import local classes and interfaces

© Copyright . All rights reserved.

Lesson: Defining and Implementing Global Interfaces

Definition of Global Interfaces

Figure 114: Defining Global Interfaces

You create global interfaces like you create global classes. Right click in the Object Navigator. The naming convention is IF_ for SAP interfaces and ZIF_ or YIF_ for user-defined interfaces.

© Copyright . All rights reserved.

281

Unit 6: Object-Oriented Repository Objects

Implementation of Global Interfaces

Figure 115: Including Global Interfaces

If you want to include a global interface in your global class, you must enter the name of the interface on the Interfaces tab page. Once you have done that, all of the interface’s components automatically appear on the relevant tab pages according to the naming convention and the interface resolution operator. In the example, the global interface ZIF_00_PARTNER containing the method DISPLAY_PARTNER is incorporated. Double-click the method name to implement the method.

282

© Copyright . All rights reserved.

Lesson: Defining and Implementing Global Interfaces

Import of Local Classes and Interfaces

Figure 116: Importing a Local Program Class

The following procedure is an easy way to make global copies of local classes and local interfaces.

Hint: The function to copy local classes to global classes cannot be used from within OBJECT-NAVIGATOR.

To Import Local Classes and Interfaces The steps to import local classes and interfaces are as follows: 1. On the SAP Easy Access screen, choose Tools → ABAP Workbench → Development → Class Builder or call transaction SE24. 2. On the Class Builder: Initial Screen, choose Object type → Import → Local classes in program. 3. In the Import from Program dialog box, enter the name of the main program and, if the local classes and interfaces were defined within include programs, select Expand include checkbox. 4. Choose the Display Classes/Interfaces pushbutton. 5. Enter names for the global classes and interfaces that you want to create. 6. Remember the customer namespace, if applicable. 7. Choose the global classes and interfaces that you want to create and choose the Import pushbutton.

© Copyright . All rights reserved.

283

Unit 6: Object-Oriented Repository Objects

284

© Copyright . All rights reserved.

Unit 6 Exercise 17 Import and Implement a Global Interface

Business Example Add a hotel as a new business partner in your program for managing a travel agency’s business partners. Template: SAPBC401_EVE_S2 (program) CL_HOTEL (global class) Solution: SAPBC401_GCL_S1 (program) CL_HOTEL2 (global class) IF_PARTNER (global interface) Task 1 Create a global interface for generalized access to business partner instances. 1. If applicable, change the interface name in your UML diagram to ZIF_##_PARTNERS. (## is your two-digit group number). 2. Create the global interface ZIF_##_PARTNER. Define the instance method DISPLAY_PARTNER in your global interface. If the local interface contains the event PARTNER_CREATED, define the event in your global interface also. Hint: Instead of creating the global interface manually you can import the local interface from your program ZBC401_##_MAIN or the template program.

Task 2 Create a global interface for generalized access to business partner instances. Replace the local interface in your main program with the global interface. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the template program. 2. Completely remove the definition of the local interface.

© Copyright . All rights reserved.

285

Unit 6: Object-Oriented Repository Objects

3. Adapt all places where the local interface was used so that the global interface is used and implemented instead. Hint: Use Find/Replace function of the ABAP Editor to reduce the typing efforts.

Task 3 Program your hotel class to implement the interface and test your program. 1. Complete your global class ZCL_##_HOTEL (where ## is your two-digit group number) or copy the template class. 2. In your main program, replace the reference to the template class with a reference to your own class. 3. If necessary, add the class ZCL_##_HOTEL to your UML diagram. The class ZCL_##_HOTEL implements the interface method DISPLAY_PARTNER and triggers the instance event PARTNER_CREATED. Draw the relationships in your diagram. 4. Declare the interface as an implemented interface in your hotel class. 5. Implement the interface method in such a way that the hotel’s DISPLAY_ATTRIBUTES instance method is called. 6. Activate the global class and your program. Run your program. If you have done everything correctly, the hotel attributes now appear on the list. If the hotel attributes do not appear on the list, Otherwise, debug your program and analyze any errors that may have occurred.

286

© Copyright . All rights reserved.

Unit 6 Solution 17 Import and Implement a Global Interface

Business Example Add a hotel as a new business partner in your program for managing a travel agency’s business partners. Template: SAPBC401_EVE_S2 (program) CL_HOTEL (global class) Solution: SAPBC401_GCL_S1 (program) CL_HOTEL2 (global class) IF_PARTNER (global interface) Task 1 Create a global interface for generalized access to business partner instances. 1. If applicable, change the interface name in your UML diagram to ZIF_##_PARTNERS. (## is your two-digit group number). a) Speak to your instructor if you have any questions. 2. Create the global interface ZIF_##_PARTNER. Define the instance method DISPLAY_PARTNER in your global interface. If the local interface contains the event PARTNER_CREATED, define the event in your global interface also. Hint: Instead of creating the global interface manually you can import the local interface from your program ZBC401_##_MAIN or the template program. a) Follow the processes as outlined in the relevant section of this lesson. Speak to your instructor if you have any questions. Task 2 Create a global interface for generalized access to business partner instances. Replace the local interface in your main program with the global interface. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number) or copy the template program.

© Copyright . All rights reserved.

287

Unit 6: Object-Oriented Repository Objects

a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 2. Completely remove the definition of the local interface. a) See source text excerpt from the model solution. 3. Adapt all places where the local interface was used so that the global interface is used and implemented instead. Hint: Use Find/Replace function of the ABAP Editor to reduce the typing efforts.

a) See source text excerpt from the model solution. Task 3 Program your hotel class to implement the interface and test your program. 1. Complete your global class ZCL_##_HOTEL (where ## is your two-digit group number) or copy the template class. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 2. In your main program, replace the reference to the template class with a reference to your own class. a) See source text excerpt from the model solution. 3. If necessary, add the class ZCL_##_HOTEL to your UML diagram. The class ZCL_##_HOTEL implements the interface method DISPLAY_PARTNER and triggers the instance event PARTNER_CREATED. Draw the relationships in your diagram. a) Speak to your instructor if you have any questions. 4. Declare the interface as an implemented interface in your hotel class. a) Follow the processes as outlined in the relevant section of this lesson. 5. Implement the interface method in such a way that the hotel’s DISPLAY_ATTRIBUTES instance method is called. a) Follow the processes as outlined in the relevant section of this lesson. 6. Activate the global class and your program. Run your program. If you have done everything correctly, the hotel attributes now appear on the list. If the hotel attributes do not appear on the list, Otherwise, debug your program and analyze any errors that may have occurred. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. Include BC401_GCL_S2_AGENCY *------------------------------------------------* * INTERFACE lif_partners *------------------------------------------------* *INTERFACE lif_partner.

288

© Copyright . All rights reserved.

Lesson: Defining and Implementing Global Interfaces

* METHODS: * display_partner. * EVENTS: * partner_created. *ENDINTERFACE.

"lif_partners

*------------------------------------------------* * CLASS lcl_travel_agency DEFINITION *------------------------------------------------* CLASS lcl_travel_agency DEFINITION. PUBLIC SECTION. METHODS: constructor IMPORTING iv_name TYPE string, display_agency_partners, display_attributes. PRIVATE SECTION. DATA: mv_name TYPE string, mt_partners TYPE TABLE OF REF TO if_partner. METHODS: on_partner_created FOR EVENT partner_created OF if_partner IMPORTING sender. ENDCLASS.

"lcl_travel_agency DEFINITION

*------------------------------------------------* * CLASS lcl_travel_agency IMPLEMENTATION *------------------------------------------------* CLASS lcl_travel_agency IMPLEMENTATION. METHOD display_attributes. WRITE: / icon_private_files AS ICON, 'Travel Agency:'(007), mv_name. SKIP. display_agency_partners( ). ENDMETHOD. "display_attributes METHOD display_agency_partners. DATA: lo_partner TYPE REF TO if_partner. WRITE 'Here are the partners of the travel agency:'(008). ULINE. LOOP AT mt_partners INTO lo_partner. lo_partner->display_partner( ). ENDLOOP. ENDMETHOD. METHOD

"display_agency_partners

constructor.

© Copyright . All rights reserved.

289

Unit 6: Object-Oriented Repository Objects

mv_name = iv_name. SET HANDLER on_partner_created FOR ALL INSTANCES. ENDMETHOD. "constructor METHOD on_partner_created. APPEND sender TO mt_partners. ENDMETHOD. "on_partner_created ENDCLASS.

"lcl_travel_agency IMPLEMENTATION Include BC401_GCL_S2_CARRIER

... *---------------------------------------------------* * CLASS lcl_carrier DEFINITION *---------------------------------------------------* CLASS lcl_carrier DEFINITION. PUBLIC SECTION. INTERFACES if_partner. METHODS: constructor IMPORTING iv_name TYPE string, on_airplane_created FOR EVENT airplane_created OF lcl_airplane IMPORTING sender, display_attributes. PRIVATE SECTION. DATA: mv_name TYPE string, mt_airplanes TYPE TABLE OF REF TO lcl_airplane. METHODS: display_airplanes. ENDCLASS.

"lcl_carrier DEFINITION

*-------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *-------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. METHOD constructor. mv_name = iv_name. SET HANDLER on_airplane_created FOR ALL INSTANCES. RAISE EVENT if_partner~partner_created. ENDMETHOD. "constructor METHOD if_partner~display_partner. display_attributes( ). ENDMETHOD. "if_partners~display_partner METHOD on_airplane_created. APPEND sender TO mt_airplanes. ENDMETHOD. "on_airplane_created

290

© Copyright . All rights reserved.

Lesson: Defining and Implementing Global Interfaces

METHOD display_attributes. SKIP 2. WRITE: icon_flight AS ICON, mv_name. ULINE. ULINE. display_airplanes( ). ENDMETHOD. "display_attributes METHOD display_airplanes. DATA: lo_plane TYPE REF TO lcl_airplane. LOOP AT mt_airplanes INTO lo_plane. lo_plane->display_attributes( ). ENDLOOP. ENDMETHOD. "display_airplanes ENDCLASS.

"lcl_carrier IMPLEMENTATION Include Program BC401_GCL_S2_RENTAL

... *---------------------------------------------------* * CLASS lcl_rental DEFINITION *---------------------------------------------------* CLASS lcl_rental DEFINITION. PUBLIC SECTION. INTERFACES: if_partner. METHODS: constructor IMPORTING iv_name TYPE string, on_vehicle_created FOR EVENT vehicle_created OF lcl_vehicle IMPORTING sender, display_attributes. PRIVATE SECTION. DATA: mv_name TYPE string, mt_vehicles TYPE TABLE OF REF TO lcl_vehicle. ENDCLASS. "lcl_rental DEFINITION *---------------------------------------------------* * CLASS lcl_rental IMPLEMENTATION *---------------------------------------------------* CLASS lcl_rental IMPLEMENTATION. METHOD if_partner~display_partner. display_attributes( ). ENDMETHOD. "if_partners~display_partner METHOD constructor. mv_name = iv_name. SET HANDLER on_vehicle_created FOR ALL INSTANCES. RAISE EVENT if_partner~partner_created. ENDMETHOD. "constructor

© Copyright . All rights reserved.

291

Unit 6: Object-Oriented Repository Objects

METHOD on_vehicle_created. APPEND sender TO mt_vehicles. ENDMETHOD. "on_vehicle_created METHOD display_attributes. DATA: lo_vehicle TYPE REF TO lcl_vehicle. WRITE: / icon_transport_proposal AS ICON, mv_name. WRITE: / 'Here comes the vehicle list: '. ULINE. ULINE. LOOP AT mt_vehicles INTO lo_vehicle. lo_vehicle->display_attributes( ). ENDLOOP. ENDMETHOD. "display_attributes ENDCLASS.

292

"lcl_rental IMPLEMENTATION

© Copyright . All rights reserved.

Lesson: Defining and Implementing Global Interfaces

LESSON SUMMARY You should now be able to: ●

Define and implement global interfaces



Import local classes and interfaces

© Copyright . All rights reserved.

293

Unit 6 Lesson 3 Implementing Inheritance in Global Classes

LESSON OVERVIEW This lesson explains how to generate UML diagrams using inheritance in global classes. Business Example As a developer, you need to generate UML diagrams which help you to keep an overview over your global classes and their relationships to each other. Additionally, you need to improve the implementation of your hotel class by using inheritance. For this reason, you require the following knowledge: ●

An understanding of how to generate UML diagrams



An understanding of how to handle global classes



An understanding of how to use refactoring assistant

LESSON OBJECTIVES After completing this lesson, you will be able to:

294



Generate UML diagrams for global classes



Implement inheritance in global classes



Handle global classes



Use the Refactoring Assistant

© Copyright . All rights reserved.

Lesson: Implementing Inheritance in Global Classes

Generation of UML Diagrams for Global Classes

Figure 117: Generate a UML Diagram for Package

As of SAP NetWeaver 7.0 Enhancement Package 2 (EhP2), the Class Builder can generate UML diagrams for existing coding. This function is restricted to global classes and does not apply to local classes. However, the diagrams can include objects from ABAP Dictionary. The figure shows how to start the functionality for a complete package. On a pop-up window, you can add a selection of objects and specify which details you want to see on the diagram.

© Copyright . All rights reserved.

295

Unit 6: Object-Oriented Repository Objects

Definition of Inheritance in Global Classes

Figure 118: Defining an Inheritance Relationship

Set out the inheritance relationships between global classes on the Properties tab page. Choose the Superclass pushbutton to specify a superclass. In the example shown in the figure, the subclass ZCL_CARGO_PLANE_00 inherits from superclass ZCL_AIRPLANE_00.

Redefinition of a Method in Global Class

Figure 119: Redefining an Inherited Method

296

© Copyright . All rights reserved.

Lesson: Implementing Inheritance in Global Classes

To redefine an inherited method, select the relevant method in the list and choose the Redefine pushbutton. Alternatively, you can use the context menu in the navigation area.

Note: The appearance of some of the icons or menus depends on the release level. The icon for redefining methods is one example.

Hint: To define the constructor in the subclass, choose the CONSTRUCTOR pushbutton in the application toolbar. The system then proposes transferring the signature of the superclass constructor. This is helpful when you want to create the subclass constructor. You can add some parameters here. Similarly, you can find the call for the superclass here.

Definition of Local Types in Global Classes

Figure 120: Defining a Local Type

You can define local types in global classes. Global classes includes local classes. Technically, you are not defining a class within a class, but a class that is local in the repository object of the global class. All components of the global class have access to these local types, but they are encapsulated if you try to access them from outside. The same applies for local interfaces in global classes. To edit the implementation parts of these local classes, choose the Impl pushbutton.

© Copyright . All rights reserved.

297

Unit 6: Object-Oriented Repository Objects

Display of Class Components

Figure 121: Structured Display of Inherited Components

To improve your understanding of inheritance and interface components, you can set the Group by Classes and Interfaces flag in the User-Specific Settings for the Class Builder. The system will then display the components of the global class in a group. Sorting the Component Display of Global Classes

Figure 122: Sorting the Component Display of Global Classes

You can sort all components by five criteria in three levels.Choose the Sort pushbutton to display the appropriate dialog box. .

298

© Copyright . All rights reserved.

Lesson: Implementing Inheritance in Global Classes

The Refactoring Assistant

Figure 123: Working with the Refactoring Assistant

Classes, interfaces and the associations between them are manifested by your ABAP implementation. Due to new business requirements you may wish to adapt and extend your ABAP implementation. Such adaptions are commonly called refactoring. The SAP Refactoring Assistant helps you to easily adapt the hierarchy and associations of classes and interfaces. For example, you can use the Refactoring Assistant to move the components of a class within the inheritance hierarchy. For a complete list of the features in this tool, refer to the SAP Library. Working with the tool is simple, because it is based on Drag and Drop dialogs.

Hint: The Tool Info pushbutton opens the SAP Library article about the Refactoring Assistant. There you can also find the descriptions about other abilities of the tool. Generally, the Refactoring Assistant does not adjust the implementation of methods. After using the Refactoring Assistant, you must check and adjust the method implementations manually. To Move a Method Definition from a Global Class to a Global Interface To move a method definition from a global class to a global interface, proceed as follows: 1. Change to the editing mode of a global class that implements a global interface. 2. Choose Tools → Refactoring Assistant. 3. In the tree structure that appears, open the folder for the method you want to move and the folder for target, which in this case, is implemented interface.

© Copyright . All rights reserved.

299

Unit 6: Object-Oriented Repository Objects

4. Move the method to the interface. 5. Choose Save. 6. If necessary, adapt statements calling the method in the source code. 7. Activate both the class and the interface.

300

© Copyright . All rights reserved.

Unit 6 Exercise 18 Implement Inheritance in Global Classes

Business Example Use inheritance and work with the Refactoring Assistant. Template: CL_HOTEL2 (global class) Solution: CL_HOTEL 3 (global class) CL_HOUSE (global class) Task 1 Define a global superclass for houses and have your hotel class inherit from it. 1. If necessary, add the class ZCL_##_HOUSE to your UML diagram. (## is your two-digit group number.) The class ZCL_##_HOUSE defines the attribute MV_NAME and the method DISPLAY_ATTRIBUTES. The class ZCL_##_HOTEL will inherit from the class ZCL_##_HOUSE. Draw the relationships in your UML diagram. 2. Create the global class ZCL_##_HOUSE and leave it empty. Caution: Make sure you deselect the final checkbox. The meaning of this property is explained in the next lesson. Speak to your instructor if you have any questions. 3. Define an inheritance relationship to make ZCL_##_HOUSE the superclass and ZCL_##_HOTEL the subclass. Speak to your instructor if you have any questions.

Task 2 Move the general components of the ZCL_##_HOTEL class to the superclass. 1. Use the Refactoring Assistant to move the c_POS_1 constant, the MV_NAME attribute, the instance constructor, and the DISPLAY_ATTRIBUTES method into the class ZCL_##_HOUSE. Speak to your instructor if you have any questions.

© Copyright . All rights reserved.

301

Unit 6: Object-Oriented Repository Objects

2. Adapt the signature and the implementation of the instance constructor in the superclass. Speak to your instructor if you have any questions. 3. Adapt the implementation of the DISPLAY_ATTRIBUTES method in the superclass. Speak to your instructor if you have any questions. 4. Define and implement the instance constructor for the superclass. Speak to your instructor if you have any questions. 5. Redefine the DISPLAY_ATTRIBUTES method in the subclass. Hint: To make constant C_POS_1 available in the implementation of DISPLAY_ATTRIBUTES of the subclass, you must change its visibility to protected. Speak to your instructor if you have any questions. 6. Observe the execution of the program in the ABAP Debugger.

302

© Copyright . All rights reserved.

Unit 6 Solution 18 Implement Inheritance in Global Classes

Business Example Use inheritance and work with the Refactoring Assistant. Template: CL_HOTEL2 (global class) Solution: CL_HOTEL 3 (global class) CL_HOUSE (global class) Task 1 Define a global superclass for houses and have your hotel class inherit from it. 1. If necessary, add the class ZCL_##_HOUSE to your UML diagram. (## is your two-digit group number.) The class ZCL_##_HOUSE defines the attribute MV_NAME and the method DISPLAY_ATTRIBUTES. The class ZCL_##_HOTEL will inherit from the class ZCL_##_HOUSE. Draw the relationships in your UML diagram. a) Speak to your instructor if you have any questions. 2. Create the global class ZCL_##_HOUSE and leave it empty. Caution: Make sure you deselect the final checkbox. The meaning of this property is explained in the next lesson. a) Follow the processes as outlined in the relevant section of this lesson. Speak to your instructor if you have any questions. 3. Define an inheritance relationship to make ZCL_##_HOUSE the superclass and ZCL_##_HOTEL the subclass. a) Follow the processes as outlined in the relevant section of this lesson. Speak to your instructor if you have any questions.

Task 2 Move the general components of the ZCL_##_HOTEL class to the superclass.

© Copyright . All rights reserved.

303

Unit 6: Object-Oriented Repository Objects

1. Use the Refactoring Assistant to move the c_POS_1 constant, the MV_NAME attribute, the instance constructor, and the DISPLAY_ATTRIBUTES method into the class ZCL_##_HOUSE. a) Follow the processes as outlined in the relevant section of this lesson. Speak to your instructor if you have any questions. 2. Adapt the signature and the implementation of the instance constructor in the superclass. a) Follow the processes as outlined in the relevant section of this lesson. Speak to your instructor if you have any questions. 3. Adapt the implementation of the DISPLAY_ATTRIBUTES method in the superclass. a) Follow the processes as outlined in the relevant section of this lesson. Speak to your instructor if you have any questions. 4. Define and implement the instance constructor for the superclass. a) Follow the processes as outlined in the relevant section of this lesson. Speak to your instructor if you have any questions. 5. Redefine the DISPLAY_ATTRIBUTES method in the subclass. Hint: To make constant C_POS_1 available in the implementation of DISPLAY_ATTRIBUTES of the subclass, you must change its visibility to protected. a) Follow the processes as outlined in the relevant section of this lesson. Speak to your instructor if you have any questions. 6. Observe the execution of the program in the ABAP Debugger. a) Carry out this step in the usual manner. For more information, refer to the SAP Library.

304

© Copyright . All rights reserved.

Lesson: Implementing Inheritance in Global Classes

LESSON SUMMARY You should now be able to: ●

Generate UML diagrams for global classes



Implement inheritance in global classes



Handle global classes



Use the Refactoring Assistant

© Copyright . All rights reserved.

305

Unit 6: Object-Oriented Repository Objects

306

© Copyright . All rights reserved.

Unit 6 Learning Assessment

1. You should use local classes or interfaces only within the program in which they are defined and implemented. Determine whether this statement is true or false. X

True

X

False

2. Which of the following are used to test the triggering of events in a class in the test environment? Choose the correct answers. X

A Select an event

X

B Choose Handler

X

C Call a method that triggers the event

3. You cannot convert to functional modern writing style when generating method calls in SAP NetWeaver (NW) Application Server (AS) 7.0. Determine whether this statement is true or false. X

True

X

False

4. The naming convention for SAP interfaces is ZIF_ or YIF_. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

307

Unit 6: Learning Assessment

5. An interface object can be used to call a method from the implementing class of the interface. Determine whether this statement is true or false. X

True

X

False

6. Which of the following is used to generate UML diagrams for existing coding? Choose the correct answer. X

A Class Builder

X

B Superclass

X

C Methods

X

D Interfaces

7. Which of the following pushbutton is used to override an inherited method? Choose the correct answer. X

A CONSTRUCTOR

X

B Redefine

X

C Implementation

8. Local types of the global class are encapsulated and cannot be accessed from outside. Determine whether this statement is true or false. X

True

X

False

9. You cannot use the Refactoring Assistant to move the components of a class within the inheritance hierarchy. Determine whether this statement is true or false.

308

X

True

X

False

© Copyright . All rights reserved.

Unit 6 Learning Assessment - Answers

1. You should use local classes or interfaces only within the program in which they are defined and implemented. Determine whether this statement is true or false. X

True

X

False

2. Which of the following are used to test the triggering of events in a class in the test environment? Choose the correct answers. X

A Select an event

X

B Choose Handler

X

C Call a method that triggers the event

3. You cannot convert to functional modern writing style when generating method calls in SAP NetWeaver (NW) Application Server (AS) 7.0. Determine whether this statement is true or false. X

True

X

False

4. The naming convention for SAP interfaces is ZIF_ or YIF_. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

309

Unit 6: Learning Assessment - Answers

5. An interface object can be used to call a method from the implementing class of the interface. Determine whether this statement is true or false. X

True

X

False

6. Which of the following is used to generate UML diagrams for existing coding? Choose the correct answer. X

A Class Builder

X

B Superclass

X

C Methods

X

D Interfaces

7. Which of the following pushbutton is used to override an inherited method? Choose the correct answer. X

A CONSTRUCTOR

X

B Redefine

X

C Implementation

8. Local types of the global class are encapsulated and cannot be accessed from outside. Determine whether this statement is true or false. X

True

X

False

9. You cannot use the Refactoring Assistant to move the components of a class within the inheritance hierarchy. Determine whether this statement is true or false.

310

X

True

X

False

© Copyright . All rights reserved.

UNIT 7

ABAP Object-Oriented Examples

Lesson 1 Implementing ABAP List Viewer (ALV) Exercise 19: Implement the ALV Grid Control Exercise 20: Implement a Popup with the ALV Grid Control

312 319 325

Lesson 2 Implementing Business Add-Ins (BAdIs)

334

UNIT OBJECTIVES ●

Implement simple ABAP List Viewer (ALV)



Implement double-click on ABAP List Viewer (ALV)



Describe Business Add-Ins (BAdIs)

© Copyright . All rights reserved.

311

Unit 7 Lesson 1 Implementing ABAP List Viewer (ALV)

LESSON OVERVIEW This lesson shows you how to implement ABAP List Viewer (ALV). Business Example You need to create a report using the ALV Grid Control. For this reason, you require the following knowledge: ●

An understanding of the ALV Grid Control



An understanding of usage of an ALV in a screen area



An understanding of how to implement ALV



An understanding of implementation of a handler for the double-click event



An understanding of how to implement an event handler for the ALV Grid Control



An understanding of how to implement a popup with the ALV Grid Control

LESSON OBJECTIVES After completing this lesson, you will be able to:

312



Implement simple ABAP List Viewer (ALV)



Implement double-click on ABAP List Viewer (ALV)

© Copyright . All rights reserved.

Lesson: Implementing ABAP List Viewer (ALV)

The ALV Grid Control

Figure 124: The ALV Grid Control

The topics illustrate the possible application areas of object-oriented ABAP programming and the use of SAP standard classes. For example, ALV Grid Control in the context of the Control Framework and the Business Add-Ins (BAdIs). The SAP Control Framework is a collection of global classes and interfaces that you can use to add SAP GUI controls in your ABAP Objects programs, regardless of the platform. The ALV Grid Control is a tool that you can use to display non-hierarchical lists in a standardized form. The list data displays in tables. It is easy to work with the tool , as there are very few programming steps that must be carried out. The ALV Grid Control contains a number of interactive standard functions that users of lists often need, for example, print, export, and so on. As a developer, you have the option of hiding these standard functions. When required, you can adapt the implementations to fit the needs of your application. You can also add your own functions to the application toolbar.

© Copyright . All rights reserved.

313

Unit 7: ABAP Object-Oriented Examples

Including an ALV Grid Control Instance in a Dialog Program

Figure 125: Including an ALV Grid Control Instance in a Dialog Program

Container Controls provide the technical connection between the screen and application controls. The application controls,such as ALV Grid Control, Tree Control, Picture Control, and so on, are always embedded in this Container Control, which, in turn, is connected to the screen. There are different types of container controls. However, all incorporate fundamental control functions, such as scroll bars.

Usage of an ALV in a Screen Area

Figure 126: Displaying Application Data Using an ALV Grid Instance

314

© Copyright . All rights reserved.

Lesson: Implementing ABAP List Viewer (ALV)

You must place an ALV Grid Control in a screen area with a fixed size. To do this, you must create an instance of each of the global classes CL_GUI_CUSTOM_CONTAINER and CL_GUI_ALV_GRID. For normal display, perform the following programming steps: 1. Use the full screen editor of the Screen Painter to define a custom control area on your screen. 2. Create an instance of the class CL_GUI_CUSTOM_CONTAINER and transfer the name of the custom control area to the constructor. 3. Create an instance of the class CL_GUI_GUI_ALV_GRID and transfer the reference to the custom control instance to the constructor. 4. Call the method SET_TABLE_FOR_FIRST_DISPLAY of the grid control instance and transfer the internal standard table to it, which contains the data to be displayed.. If the table has a global row type defined in ABAP Dictionary, you can transfer the name of this global structure to the same method.The ALV Grid Control then automatically creates the field catalog.

Caution: The internal table transferred to the method SET_TABLE_FOR_FIRST_DISPLAY must be globally defined. Therefore, the table must be either a global program variable or a public attribute of a class. When you change the contents of the internal tables while the program is running, you only need to call the method REFRESH_TABLE_DISPLAY in the relevant dialog step to refresh the display.

Implementation of a Handler for the Double-Click Event

Figure 127: ALV Grid Control – Double-Click

© Copyright . All rights reserved.

315

Unit 7: ABAP Object-Oriented Examples

An ALV Grid Control can react to the user’s double-click. As a possible reaction, you can trigger a follow-on processing step in which additional information is displayed. In the example shown in the figure, the booking data for the individual flight customers or data on the aircraft, can also be displayed for the flight data. This is executed by catching the event DOUBLE_CLICK with a handler method. ALV Grid Control – Reacting to a Double-Click

Figure 128: ALV Grid Control – Reacting to a Double-Click

A handler method is a class method (static method) or an instance method of an object. If a class method is defined as a handler method, no object of the handled class needs to be instantiated to use the method. To create a handler object for an event, define a class. This class has a public method in the public section that can react to an event. During the implementation of the handler method, define the source text that must be run when the event is triggered. The method receives the information that the event delivers from the mouse position when you double-click, and creates an information message in the control example that displays the row and field of the mouse click.

316

© Copyright . All rights reserved.

Lesson: Implementing ABAP List Viewer (ALV)

Note: Extensive documentation about the SAP Control Framework is available in the standard SAP product documentation (delivered with the product or online through the SAP Help portal). The SAP Library contains comprehensive descriptions of all classes and a complete tutorial. The ABAP Workbench Object Navigator also contains the Demo Center, which makes it very easy to use standard template programs. You can find the ABAP Workbench Object Navigator under Environment →  Examples → Controls Examples. Individual elements of the SAP Control Framework are covered in other courses. SAP also offers a separate comprehensive course about dialog programming with the SAP controls. The course covers all aspects, including complex programming techniques such as the drag and drop functions.

© Copyright . All rights reserved.

317

Unit 7: ABAP Object-Oriented Examples

318

© Copyright . All rights reserved.

Unit 7 Exercise 19 Implement the ALV Grid Control

Business Example You want to see a list of flight connections in an ALV Grid Control. When you double-click a connection, the selected row number and column name must display. Template: SAPBC401_ALV_T1 Solution: SAPBC401_ALV_S1 Create an ALV Grid Control, and react to double-click on the ALV Grid Control. Task 1 Programming  an ALV Grid Control and displaying the list of flight connections already stored in internal table GT_SPFLI. 1. Copy the template program SAPBC401_ALV_T1 to ZBC401_##_ALV. 2. In the main program, define the reference variables GO_CONTAINER and GO_ALV_GRID required for the ALV Grid Control. 3. Analyze the existing screen 100, paying particular attention to the name of the Custom Container Control Area, which is used as the basis for the ALV Grid Control. Implement the PBO module ALV_GRID. Use the reference variables to instantiate the two classes in this PBO module. Pay attention to the fact that the CREATE OBJECT is not called repeatedly when the PBO is executed repeatedly. 4. To display data in the ALV Grid Control, call the method SET_TABLE_FOR_FIRST_DISPLAY and transfer the internal table with the flight connection data and the name of the line type of that internal table. 5. Activate and test your program. Caution: You are working with a screen in this exercise, so always activate all parts of the program as well as the screen.

Task 2 Handle a double-click on the ALV Grid Control.

© Copyright . All rights reserved.

319

Unit 7: ABAP Object-Oriented Examples

If the user double-clicks a row in the ALV Grid Control, the row number and column name where the user double-clicked should be displayed in a message of type I. 1. Define a local class LCL_EVENT_HANDLER, and in this class, define an instance method to handle the event DOUBLE_CLICK that the ALV Grid Control triggered. Note: The class LCL_EVENT_HANDLER only acts as a handler and, otherwise, does not have any other functions. Import parameters ES_ROW_NO and E_COLUMN into the handler method. 2. Implement the handler method. Send a message of type I to output the row number and column name the user clicked. 3. Instantiate the handler class, and register the event handler method. 4. Activate and test your program.

320

© Copyright . All rights reserved.

Unit 7 Solution 19 Implement the ALV Grid Control

Business Example You want to see a list of flight connections in an ALV Grid Control. When you double-click a connection, the selected row number and column name must display. Template: SAPBC401_ALV_T1 Solution: SAPBC401_ALV_S1 Create an ALV Grid Control, and react to double-click on the ALV Grid Control. Task 1 Programming  an ALV Grid Control and displaying the list of flight connections already stored in internal table GT_SPFLI. 1. Copy the template program SAPBC401_ALV_T1 to ZBC401_##_ALV. a) Carry out this step in the usual manner. 2. In the main program, define the reference variables GO_CONTAINER and GO_ALV_GRID required for the ALV Grid Control. a) Review the source code extract from the model solution or refer to the corresponding slides about the ALV Grid Control. 3. Analyze the existing screen 100, paying particular attention to the name of the Custom Container Control Area, which is used as the basis for the ALV Grid Control. Implement the PBO module ALV_GRID. Use the reference variables to instantiate the two classes in this PBO module. Pay attention to the fact that the CREATE OBJECT is not called repeatedly when the PBO is executed repeatedly. a) Review the source code extract from the model solution, or refer to the corresponding slides about the ALV Grid Control. Speak to your instructor if you have any questions. 4. To display data in the ALV Grid Control, call the method SET_TABLE_FOR_FIRST_DISPLAY and transfer the internal table with the flight connection data and the name of the line type of that internal table. a) Review the source code extract from the model solution, or refer to the corresponding slides about the ALV Grid Control. Speak to your instructor if you have any questions. 5. Activate and test your program.

© Copyright . All rights reserved.

321

Unit 7: ABAP Object-Oriented Examples

Caution: You are working with a screen in this exercise, so always activate all parts of the program as well as the screen. a) Carry out this step in the usual manner.

Task 2 Handle a double-click on the ALV Grid Control. If the user double-clicks a row in the ALV Grid Control, the row number and column name where the user double-clicked should be displayed in a message of type I. 1. Define a local class LCL_EVENT_HANDLER, and in this class, define an instance method to handle the event DOUBLE_CLICK that the ALV Grid Control triggered. Note: The class LCL_EVENT_HANDLER only acts as a handler and, otherwise, does not have any other functions. Import parameters ES_ROW_NO and E_COLUMN into the handler method. a) See the source code extract from the model solution, or refer to the corresponding slides on how to double-click the ALV Grid Control. 2. Implement the handler method. Send a message of type I to output the row number and column name the user clicked. a) You can use message 010 of message class BC401. 3. Instantiate the handler class, and register the event handler method. a) Review the source code extract from the model solution or refer to the corresponding slides on how to double-click the ALV Grid Control. 4. Activate and test your program. a) Carry out this step in the usual manner. Make sure that the program displays as follows: SAPBC401_ALV_S1 REPORT

sapbc401_alv_s1.

*-------------------------------------------------* * CLASS lcl_event_handler DEFINITION *-------------------------------------------------* CLASS lcl_event_handler DEFINITION. PUBLIC SECTION. METHODS on_double_click FOR EVENT double_click OF cl_gui_alv_grid IMPORTING es_row_no e_column.

322

© Copyright . All rights reserved.

Lesson: Implementing ABAP List Viewer (ALV)

ENDCLASS.

"lcl_event_handler DEFINITION

*-------------------------------------------------* * CLASS lcl_event_handler IMPLEMENTATION *-------------------------------------------------* CLASS lcl_event_handler IMPLEMENTATION. METHOD on_double_click. MESSAGE i010(bc401) WITH es_row_no-row_id e_column-fieldname. ENDMETHOD. ENDCLASS.

"handler_method "lcl_event_handler IMPLEMENTATION

*** Types and Data Definitions TYPES: ty_spfli TYPE STANDARD TABLE OF spfli WITH NON-UNIQUE KEY carrid connid. DATA: ok_code TYPE sy-ucomm. DATA: go_handler TYPE REF TO lcl_event_handler, go_container TYPE REF TO cl_gui_custom_container, go_alv_grid TYPE REF TO cl_gui_alv_grid. DATA: gt_spfli TYPE ty_spfli.

START-OF-SELECTION. ******************** SELECT * FROM spfli INTO TABLE gt_spfli. CALL SCREEN '0100'. *&----------------------------------------------* *& Module STATUS_0100 OUTPUT *&----------------------------------------------* MODULE status_0100 OUTPUT. SET PF-STATUS 'DYNPROSTATUS'. SET TITLEBAR 'TITLE1'. ENDMODULE. " STATUS_0100 OUTPUT *&----------------------------------------------* *& Module ALV_GRID OUTPUT *&----------------------------------------------* MODULE alv_grid OUTPUT. ** Create object of class CL_GUI_CUSTOM_CONTAINER ** to manage data IF go_container IS NOT BOUND. CREATE OBJECT go_container EXPORTING container_name = 'CONTAINER_1' EXCEPTIONS

© Copyright . All rights reserved.

323

Unit 7: ABAP Object-Oriented Examples

others = 6. IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. ** create object of class cl_gui_alv_grid to visualize data CREATE OBJECT go_alv_grid EXPORTING i_parent = go_container EXCEPTIONS others = 5. IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. ** create handler instance and register handler method CREATE OBJECT go_handler. SET HANDLER go_handler->on_double_click FOR go_alv_grid. ** Call method to visualize data of internal table CALL METHOD go_alv_grid->set_table_for_first_display EXPORTING i_structure_name = 'SPFLI' CHANGING it_outtab = gt_spfli EXCEPTIONS OTHERS = 4. IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. ENDIF. ENDMODULE.

" ALV_GRID

OUTPUT

*&-----------------------------------------------* *& Module USER_COMMAND_0100 INPUT *&-----------------------------------------------* MODULE user_command_0100 INPUT. CASE ok_code. WHEN 'BACK'. SET SCREEN 0. WHEN 'EXIT'. LEAVE PROGRAM. ENDCASE. ENDMODULE.

324

" USER_COMMAND_0100

INPUT

© Copyright . All rights reserved.

Unit 7 Exercise 20 Implement a Popup with the ALV Grid Control

Business Example You need to see a list of flight connections in an ALV Grid Control. When you double-click one connection, the list of flights for this connection must be displayed in a second ALV Grid Control. Template: SAPBC401_ALV_S1 Solution: SAPBC401_ALV_S2 Use advanced ALV Grid programming. Task 1 Read from the database table SFLIGHT about the flights that belong to the flight connection that you double-clicked. 1. Complete your program ZBC401_##_ALV (where ## is your two-digit group number) or copy the model solution from the previous exercise. 2. In the event handler method, remove the MESSAGE statement. Define a local structure (suggested name - LS_SPFLI) to serve as a work area for internal table GT_SPFLI. From GT_SPFLI, read the entry that corresponds to the grid row you double-clicked. Hint: Use READ TABLE with an index access.

3. Is defining GT_SPFLI after the definition of the event handler class acceptable?

4. In the definition of the event handler class, define a private instance attribute MT_SFLIGHT, which is an internal (standard) table with line type SFLIGHT. Hint: Define a private table type TY_SFLIGHT in the same class.

© Copyright . All rights reserved.

325

Unit 7: ABAP Object-Oriented Examples

5. In the event handler method, implement an array fetch for database table SFLIGHT to fill MT_SFLIGHT with those flights that have the same key fields as the flight connection that you have clicked. 6. Activate your program and analyze it in the ABAP Debugger. Make sure MT_SFLIGHT is filled correctly.

Task 2 Extend your event handler method so that the selected flights are presented in a second ALV Grid Control which is displayed in a dialog box. 1. In your event handler class, define two reference variables as private instance attributes (suggested names – MO_CONT_POPUP and MO_ALV_POPUP). Type them with the global classes CL_GUI_DIALOGBOX_CONTAINER and CL_GUI_ALV_GRID. 2. In your event handler method, use these reference variables to create instances of the two classes. The CREATE OBJECT is not called repeatedly when the event handler method is executed repeatedly. 3. To display data in the ALV Grid Control, call the method SET_TABLE_FOR_FIRST_DISPLAY and transfer the internal table MT_SFLIGHT with the flight data and the name of the line type of that internal table. Make sure this method is only called if the dialog box container and the second ALV Grid Control have just been created. 4. If the dialog box container and the second ALV Grid Control already exist, do not call method SET_TABLE_FOR_FIRST_DISPLAY to refresh the data displayed. Call the method REFRESH_TABLE_DISPLAY instead. Hint: You do not have to provide values for the optional parameters of this method.

5. Activate and test your program. Note: At this point, clicking the button in the top-right corner of the window does not close the dialog box container. To implement this function, you must handle event CLOSE of class CL_GUI_DIALOGBOX_CONTAINER and call method FREE of the dialog box container. Other training courses and the Control Framework documentation explain the this procedure in detail.

326

© Copyright . All rights reserved.

Unit 7 Solution 20 Implement a Popup with the ALV Grid Control

Business Example You need to see a list of flight connections in an ALV Grid Control. When you double-click one connection, the list of flights for this connection must be displayed in a second ALV Grid Control. Template: SAPBC401_ALV_S1 Solution: SAPBC401_ALV_S2 Use advanced ALV Grid programming. Task 1 Read from the database table SFLIGHT about the flights that belong to the flight connection that you double-clicked. 1. Complete your program ZBC401_##_ALV (where ## is your two-digit group number) or copy the model solution from the previous exercise. a) Carry out this step in the usual manner. 2. In the event handler method, remove the MESSAGE statement. Define a local structure (suggested name - LS_SPFLI) to serve as a work area for internal table GT_SPFLI. From GT_SPFLI, read the entry that corresponds to the grid row you double-clicked. Hint: Use READ TABLE with an index access.

a) See the source code extract from the model solution. 3. Is defining GT_SPFLI after the definition of the event handler class acceptable? No. To be able to access the global data object GT_SPFLI from within the local class implementation, the data object must be defined as global program variable before the local class definition. 4. In the definition of the event handler class, define a private instance attribute MT_SFLIGHT, which is an internal (standard) table with line type SFLIGHT.

© Copyright . All rights reserved.

327

Unit 7: ABAP Object-Oriented Examples

Hint: Define a private table type TY_SFLIGHT in the same class.

a) Review the source code extract from the model solution. 5. In the event handler method, implement an array fetch for database table SFLIGHT to fill MT_SFLIGHT with those flights that have the same key fields as the flight connection that you have clicked. a) Review the source code extract from the model solution. 6. Activate your program and analyze it in the ABAP Debugger. Make sure MT_SFLIGHT is filled correctly. a) Carry out this step in the usual manner.

Task 2 Extend your event handler method so that the selected flights are presented in a second ALV Grid Control which is displayed in a dialog box. 1. In your event handler class, define two reference variables as private instance attributes (suggested names – MO_CONT_POPUP and MO_ALV_POPUP). Type them with the global classes CL_GUI_DIALOGBOX_CONTAINER and CL_GUI_ALV_GRID. a) Review the source code extract from the model solution. 2. In your event handler method, use these reference variables to create instances of the two classes. The CREATE OBJECT is not called repeatedly when the event handler method is executed repeatedly. a) Review the source code extract from the model solution. 3. To display data in the ALV Grid Control, call the method SET_TABLE_FOR_FIRST_DISPLAY and transfer the internal table MT_SFLIGHT with the flight data and the name of the line type of that internal table. Make sure this method is only called if the dialog box container and the second ALV Grid Control have just been created. a) Review the source code extract from the model solution. 4. If the dialog box container and the second ALV Grid Control already exist, do not call method SET_TABLE_FOR_FIRST_DISPLAY to refresh the data displayed. Call the method REFRESH_TABLE_DISPLAY instead. Hint: You do not have to provide values for the optional parameters of this method.

a) Review the source code extract from the model solution.

328

© Copyright . All rights reserved.

Lesson: Implementing ABAP List Viewer (ALV)

5. Activate and test your program. Note: At this point, clicking the button in the top-right corner of the window does not close the dialog box container. To implement this function, you must handle event CLOSE of class CL_GUI_DIALOGBOX_CONTAINER and call method FREE of the dialog box container. Other training courses and the Control Framework documentation explain the this procedure in detail. a) Carry out this step in the usual manner. SAPBC401_ALV_S2 REPORT

sapbc401_alv_s2.

TYPES: ty_spfli TYPE STANDARD TABLE OF spfli WITH NON-UNIQUE KEY carrid connid. DATA: gt_spfli TYPE ty_spfli. *--------------------------------------------------* * CLASS lcl_event_handler DEFINITION *--------------------------------------------------* * *--------------------------------------------------* CLASS lcl_event_handler DEFINITION. PUBLIC SECTION. METHODS on_double_click FOR EVENT double_click OF cl_gui_alv_grid IMPORTING es_row_no e_column. PRIVATE SECTION. TYPES: ty_sflight TYPE STANDARD TABLE OF sflight WITH NON-UNIQUE KEY carrid connid fldate. DATA: mo_cont_popup TYPE REF TO cl_gui_dialogbox_container, mo_alv_popup TYPE REF TO cl_gui_alv_grid. DATA: mt_sflight TYPE ty_sflight. ENDCLASS.

"lcl_event_handler DEFINITION

*--------------------------------------------------* * CLASS lcl_event_handler IMPLEMENTATION *--------------------------------------------------* * *--------------------------------------------------* CLASS lcl_event_handler IMPLEMENTATION. METHOD on_double_click. DATA ls_spfli TYPE spfli.

© Copyright . All rights reserved.

329

Unit 7: ABAP Object-Oriented Examples

READ TABLE gt_spfli INTO ls_spfli INDEX es_row_no-row_id. SELECT * FROM sflight INTO TABLE mt_sflight WHERE carrid = ls_spfli-carrid AND connid = ls_spfli-connid. IF mo_cont_popup IS NOT BOUND. CREATE OBJECT mo_cont_popup EXPORTING width = 600 height = 300 EXCEPTIONS others = 8. IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. CREATE OBJECT mo_alv_popup EXPORTING i_parent = mo_cont_popup EXCEPTIONS others = 5. IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. mo_alv_popup->set_table_for_first_display( EXPORTING i_structure_name = 'SFLIGHT' CHANGING it_outtab = mt_sflight EXCEPTIONS OTHERS = 4 ). IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. ELSE. mo_alv_popup->refresh_table_display( EXCEPTIONS OTHERS = 2 ). IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. ENDIF. * MESSAGE i010(bc401) WITH

330

© Copyright . All rights reserved.

Lesson: Implementing ABAP List Viewer (ALV)

*

es_row_no-row_id e_column-fieldname.

ENDMETHOD. ENDCLASS.

"handler_method "lcl_event_handler IMPLEMENTATION

DATA: ok_code TYPE sy-ucomm. DATA: go_handler TYPE REF TO lcl_event_handler, go_container TYPE REF TO cl_gui_custom_container, go_alv_grid TYPE REF TO cl_gui_alv_grid. START-OF-SELECTION. ******************** SELECT * FROM spfli INTO TABLE gt_spfli. CALL SCREEN '0100'. *&------------------------------------------------* *& Module STATUS_0100 OUTPUT *&------------------------------------------------* * text *-------------------------------------------------* MODULE status_0100 OUTPUT. SET PF-STATUS 'DYNPROSTATUS'. SET TITLEBAR 'TITLE1'. ENDMODULE. " STATUS_0100 OUTPUT *&------------------------------------------------* *& Module ALV_GRID OUTPUT *&------------------------------------------------* * text *-------------------------------------------------* MODULE alv_grid OUTPUT. * Create object of class CL_GUI_CUSTOM_CONTAINER to * manage data IF go_container IS NOT BOUND. CREATE OBJECT go_container EXPORTING container_name = 'CONTAINER_1' EXCEPTIONS others = 6. IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. * create object of class cl_gui_alv_grid to visualize data CREATE OBJECT go_alv_grid EXPORTING i_parent = go_container EXCEPTIONS others = 5. IF sy-subrc 0.

© Copyright . All rights reserved.

331

Unit 7: ABAP Object-Oriented Examples

MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. ** create handler Instance CREATE OBJECT go_handler. ** set handler to react on double-click SET HANDLER go_handler->on_double_click FOR go_alv_grid. ** Call method to visualize data of internal table CALL METHOD go_alv_grid->set_table_for_first_display EXPORTING i_structure_name = 'SPFLI' CHANGING it_outtab = gt_spfli EXCEPTIONS OTHERS = 4. IF sy-subrc 0. MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4. ENDIF. ENDIF. ENDMODULE.

" ALV_GRID

OUTPUT

*&-------------------------------------------------* *& Module USER_COMMAND_0100 INPUT *&-------------------------------------------------* MODULE user_command_0100 INPUT. CASE ok_code. WHEN 'BACK'. SET SCREEN 0. WHEN 'EXIT'. LEAVE PROGRAM. ENDCASE. ENDMODULE.

332

" USER_COMMAND_0100

INPUT

© Copyright . All rights reserved.

Lesson: Implementing ABAP List Viewer (ALV)

LESSON SUMMARY You should now be able to: ●

Implement simple ABAP List Viewer (ALV)



Implement double-click on ABAP List Viewer (ALV)

© Copyright . All rights reserved.

333

Unit 7 Lesson 2 Implementing Business Add-Ins (BAdIs)

LESSON OVERVIEW This lesson shows you how to implement Business Add-Ins (BAdIs). Business Example You need to enhance functionality in an SAP standard program, without altering the original program. This can be done by using BAdIs. For this reason, you require the following knowledge: ●

An understanding of BAdI



An understanding of how to define a BAdI



An understanding of how to implement a BAdI

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Describe Business Add-Ins (BAdIs)

BAdIs Unlike Customer Exits, BAdIs are optimized for the changed software delivery process. The typical software delivery process does not only consist of providers and customers, rather several intermediate providers may be involved in the delivery chain for software. For example, an SAP partner can extend an SAP application program with an industry solution like Industrial Business Unit (IBU). The customer can then again extend the same program.

334

© Copyright . All rights reserved.

Lesson: Implementing Business Add-Ins (BAdIs)

BAdI – Basics

Figure 129: BAdI – Basics

With a BAdI, an SAP application provides the enhancement option through an interface and an adapter class implementing that interface. The interface can be implemented by several users in the delivery chain, thus, multiple BAdI implementations are possible. Additionally, a BAdI implementation itself can provide another BAdI which can be implemented by users who appear further out in the delivery chain.

© Copyright . All rights reserved.

335

Unit 7: ABAP Object-Oriented Examples

Definition of a BAdI – Basics

Figure 130: Definition of a BAdI – Basics

When you define a BAdI, you must specify an interface (IF_EX_) with corresponding formally defined methods. The adapter class that is automatically generated during the interface definition (CL_EX_) has, among other capabilities, the function of calling all active implementations of the BAdI. When you have several active implementations, there isno predefined processing sequence. To Define a BAdI

1. Run the transaction SE18 or on the SAP Easy Access screen, choose Tools → ABAP Workbench → Utilities → Business Add-Ins → Definition. 2. As of SAP Netweaver 7.0 you cannot directly create a BAdI. First, you must create a so called Enhancement Spot. Within the Enhancement Spot definition, you can then create BAdI's on the Enhancement Spot Element Definitions tab strip. 3. Enter the definition name (). 4. Choose the Create pushbutton and enter the interface name () name in the corresponding dialog box.

336

© Copyright . All rights reserved.

Lesson: Implementing Business Add-Ins (BAdIs)

BAdI – The Calling Program

Figure 131: BAdI – The Calling Program

The figure shows an example of a BadI call. A reference variable for the type of BadI must be defined. An object of the adapter class is instantiated by the call of the GET_INSTANCE static method of the CL_EXITHANDLER class. The variable gb_adapter points to this instance. The interface methods of the BAdI can be called by gb_adapter object reference.

Search for BAdIs You can search the BAdI using the following methods: ● You can use the Repository Information System (transaction SE84). ●

You can use the Application Hierarchy (transaction SE81).



You can use the Customizing Guide (Implementation guide for transaction SPRO).







You can search in the application source code for the CL_EXITHANDLER=>GET_INSTANCE statement. You can search in the application source code for the occurrence of the BAdI interfaces with the naming convention IF_EX_. As of SAP Netweaver AS 7.0, you can search in the application source code for occurrences of the GET BADI statement.

The name of the BAdl must be investigated before you can implement the BAdI. When searching for BAdI names, you can use the search mechanisms. Double-click the reference variable

© Copyright . All rights reserved.

337

Unit 7: ABAP Object-Oriented Examples

(gb_adapter) in the example to get the interface definition. You can derive the BAdI name from the name of the interface.

Note: How to search in ABAP source code: When running an arbitrary transaction press the F1 key. On the appearing popup press the Technical Information pushbutton. Navigate to the source code of the program by double-clicking the program name. Then call the global search function in menu Edit → Find Next and search for the desired string. Remark: Don't use the editor's search function Edit → Find/Replace (Ctrl-F) because this function will consider a single source code include only.

Implement a BAdI

Figure 132: Implementation of a BAdI – SE19

When the name of the BAdI is determined, the BAdI can be implemented. The implementation of the BadI is performed through the implementation maintenance under Tools → ABAP Workbench → Utilities → Business Add-Ins → Implementation (transaction code SE19). Alternatively, you can go to the implementations by navigating the menu from the BAdI definition. To implement a BAdI, a BAdI implementation name must be issued. The naming convention is Z. A dialog box then appears for selecting the corresponding BAdI. The code to be implemented is stored in a method of an automatically generated customer class. For this reason, the name of the implementing class must be given in a final dialog box. The default name from SAP  is comprised of Y or Z (the namespace prefix), CL_ (for class), IM_ (for implementation), and (the actual name of the implementation).

338

© Copyright . All rights reserved.

Lesson: Implementing Business Add-Ins (BAdIs)

When you double-click one of the BAdI methods, you can enter the code of the method.You can also create auxiliary methods in the implementing class to better structure the required code of the BAdI method.

Note: Activate the methods or the implementations at the end of the task.

To Implement a BAdI 1. Run the transaction code SE19. 2. Enter the BAdI definition name (or Enhancement Spot name) and choose the Create pushbutton. 3. Enter an implementation name and choose the OK pushbutton. 4. Enter a description text and choose the Save pushbutton. 5. Double-click the name of the implementing class to navigate to the class and implement your source code there. LESSON SUMMARY You should now be able to: ●

Describe Business Add-Ins (BAdIs)

© Copyright . All rights reserved.

339

Unit 7: ABAP Object-Oriented Examples

340

© Copyright . All rights reserved.

Unit 7 Learning Assessment

1. The ABAP List Viewer (ALV) Grid Control is a tool that you can use to display non-hierarchical lists in a standardized form. Determine whether this statement is true or false. X

True

X

False

2. Container controls do not provide the technical connection between the screen and application control. Determine whether this statement is true or false. X

True

X

False

3. To create a handler object for an event, we must first define a ____________. Choose the correct answer. X

A class

X

B structure

X

C screen

X

D attribute

4. A handler method can be either a class method (static method) or an instance method of an object. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

341

Unit 7: Learning Assessment

5. With a Business Add-In (BAdI), an SAP application program provides the enhancement option through an interface. Determine whether this statement is true or false. X

True

X

False

6. An object of the adapter class is instantiated by the call of the static method GET_INSTANCE of the class CL_EXITHANDLER. Determine whether this statement is true or false. X

True

X

False

7. To implement a Business Add-In (BAdI), the BADI definition name must be investigated. Determine whether this statement is true or false. X

True

X

False

8. The code of a BAdI implementation is stored in a __________ of an automatically generated customer class. Choose the correct answer.

342

X

A method

X

B structure

X

C object

© Copyright . All rights reserved.

Unit 7 Learning Assessment - Answers

1. The ABAP List Viewer (ALV) Grid Control is a tool that you can use to display non-hierarchical lists in a standardized form. Determine whether this statement is true or false. X

True

X

False

2. Container controls do not provide the technical connection between the screen and application control. Determine whether this statement is true or false. X

True

X

False

3. To create a handler object for an event, we must first define a ____________. Choose the correct answer. X

A class

X

B structure

X

C screen

X

D attribute

4. A handler method can be either a class method (static method) or an instance method of an object. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

343

Unit 7: Learning Assessment - Answers

5. With a Business Add-In (BAdI), an SAP application program provides the enhancement option through an interface. Determine whether this statement is true or false. X

True

X

False

6. An object of the adapter class is instantiated by the call of the static method GET_INSTANCE of the class CL_EXITHANDLER. Determine whether this statement is true or false. X

True

X

False

7. To implement a Business Add-In (BAdI), the BADI definition name must be investigated. Determine whether this statement is true or false. X

True

X

False

8. The code of a BAdI implementation is stored in a __________ of an automatically generated customer class. Choose the correct answer.

344

X

A method

X

B structure

X

C object

© Copyright . All rights reserved.

UNIT 8

Object-Oriented Design Patterns

Lesson 1 Implementing Special Object-Oriented Techniques

346

Lesson 2 Implementing the Singleton Pattern Exercise 21: Implement the Singleton Pattern

354 359

Lesson 3 Implementing Factory Classes Using Friendship Exercise 22: Implement a Factory Class Using Friendship

368 371

UNIT OBJECTIVES ●

Implement abstract classes



Implement final classes



Access internal tables with object references



Call navigation methods



Define the visibility of the instance constructor



Implement factory methods



Implement the singleton pattern



Implement friendship relationships

© Copyright . All rights reserved.

345

Unit 8 Lesson 1 Implementing Special Object-Oriented Techniques

LESSON OVERVIEW This lesson explains how to implement abstract classes and final classes, how to access internal tables with object references, and how to call the navigation methods. Business Example You need to add special object-oriented programming techniques to your ABAP Objects implementations. For this reason, you require the following knowledge: ●

An understanding of how to define abstract classes



An understanding of how to define abstract methods



An understanding of how to define final classes



An understanding of how to define final methods



An understanding of how to use public read-only attributes



An understanding of how to call navigational methods



An understanding of how to chain functional methods



An understanding of how to define the Visibility of the Instance Constructor

LESSON OBJECTIVES After completing this lesson, you will be able to:

346



Implement abstract classes



Implement final classes



Access internal tables with object references



Call navigation methods



Define the visibility of the instance constructor

© Copyright . All rights reserved.

Lesson: Implementing Special Object-Oriented Techniques

Abstract Classes

Figure 133: Abstract Classes and Abstract Methods

Abstract class contains both definition and implementation but cannot be instantiated. Use the ABSTRACT addition in the CLASS statement to create an abstract class. Super classes are a typical use for abstract classes, as they are not to be instantiated themselves, but their subclasses are. In an abstract class, you can define abstract methods among other things. This means that the abstract method cannot be implemented in that class. Instead, it is implemented in a subclass of the class.  If the subclass of that class is not abstract, the abstract methods must be redefined and implemented in the subclass for the first time.

Note: The relevant indicator is in the Class Builder on the Attributes tab for that class or method. References to such abstract classes can be used for polymorphic access to subclass instances. Static methods cannot be abstract because they cannot be redefined.

© Copyright . All rights reserved.

347

Unit 8: Object-Oriented Design Patterns

Final Classes

Figure 134: Final Classes and Methods

Prevent a class from being inherited by using the FINAL addition with the class statement. You can prevent a method from being redefined by using the FINAL addition with the methods statement.

Note: The relevant indicator is in the Class Builder on the Attributes tab for that class or method. Thus, all methods of a final class are implicitly final. You may not repeat the FINAL addition in the methods themselves. Classes that are abstract and final should only contain static components.

348

© Copyright . All rights reserved.

Lesson: Implementing Special Object-Oriented Techniques

Internal Tables with Object References

Figure 135: Read Access to a Table with Object References

Object references can be stored in internal tables. The example in the figure explains how to retrieve a specific object from such a list. The object reference is stored in the table along with some key information. In the example, the key information is the make and model of the vehicle. The object reference can easily be retrieved through this key information. This technique implies a redundant storage of information as the key values are already stored in attributes of the object.

© Copyright . All rights reserved.

349

Unit 8: Object-Oriented Design Patterns

Read Access Using Public Attributes

Figure 136: Read Access Using Public Attributes

As shown in the figure, the key information redundancy can be avoided by making the key attributes public. Public attributes can be used directly to access internal tables in the READ TABLE  and LOOP AT statement. The expression TABLE_LINE used here is a built-in part of the ABAP language. When the line type of an internal table is an elementary data type instead of a structure type, you need to use TABLE_LINE. Such internal tables have just one unnamed column. TABLE_LINE is used as the generic column name for this single column.

Hint: It is against the fundamental principles of object-oriented programming to make attributes public. Unfortunately, ABAP does not allow you to use functional methods (like the methods in our example GET_MAKE, GET_MODEL, and so on) on the lefthand side of WHERE clauses and WITH KEY additions. Therefore, public attributes are only used in some special cases in read-only mode.

350

© Copyright . All rights reserved.

Lesson: Implementing Special Object-Oriented Techniques

Call and Chain Navigation Methods

Figure 137: Navigation Methods and Chaining of Method Calls

Associations like aggregations and compositions are an important design principle of objectoriented programming. An association means that at runtime, an instance of one class stores references to objects of another class. Classes that have other classes associated with them often come with methods that return one of the stored references to the caller. Such methods are often called navigation methods, as they can be used to navigate from one object to another. In the example, the LCL_VEHICLE class is associated with the LCL_RENTAL class. Class LCL_RENTAL provides the navigation method GET_VEHICLE. Often, the purpose of navigating from one object to another is to access a single method of this other object. Before the release of SAP NetWeaver 7.0 EhP2, it was mandatory to first store the reference to the new object in a reference variable. As of SAP NetWeaver 7.0 EhP2, we can chain method calls, that is, we can directly call a method of the object that the navigation method returns.

Hint: This technique is not restricted to the chaining of two methods. In more complicated object models, it is possible to chain any number of methods.

© Copyright . All rights reserved.

351

Unit 8: Object-Oriented Design Patterns

Visibility of the Instance Constructor

Figure 138: Implicit Setting of the Instance Constructor’s Visibility

In ABAP Objects, we can restrict the visibility of the instance constructor. If the visibility of the instance constructor is restricted, the CREATE OBJECT statements to instantiate this class is only allowed in certain parts of the coding. Types of visibilities for the instance constructor, as follows: ● PRIVATE If a class has a private instance constructor, it can only be instantiated from within the class itself, typically in static methods defined for that purpose. These methods are sometimes called “Factor-Methods”. ●

PROTECTED If the instance constructor is protected, the visibility is extended to all of its subclasses, that is, the subclasses can also create instances of the class.



PUBLIC A public instance constructor is the default visibility setting : Instances of the class can be created anywhere, inside the class itself, inside other classes, or, even in a non-object-oriented part of the program (for example, the main program).

Set the visibility by using the CREATE addition with the CLASS statement.

Note: The relevant indicator is in the Class Builder on the Attributes tab for the relevant class.

352

© Copyright . All rights reserved.

Lesson: Implementing Special Object-Oriented Techniques

Hint: The visibility of the constructor is not set by placing the definition of the method CONSTRUCTOR in the respective section of the class definition. In fact, before SAP NetWeaver 7.0, it was mandatory to place the constructor syntactically in the public section. Since SAP NetWeaver 7.0, it is allowed, but not required to place the constructor in the protected or private section - if this is not more restrictive than the CREATE… addition in the class definition. This is to increase the readability of the coding.

LESSON SUMMARY You should now be able to: ●

Implement abstract classes



Implement final classes



Access internal tables with object references



Call navigation methods



Define the visibility of the instance constructor

© Copyright . All rights reserved.

353

Unit 8 Lesson 2 Implementing the Singleton Pattern

LESSON OVERVIEW This lesson explains the concepts of factory methods, the singleton pattern, and their implementation. Business Example: You need to add special object-oriented programming techniques to your ABAP Objects implementations. For this reason, you require the following knowledge: ●

An understanding of factory method



An understanding of singleton pattern

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Implement factory methods



Implement the singleton pattern

Factory Methods Restricting the visibility of the instance constructor only makes sense if somewhere within the class (or its subclasses, in case of CREATE PROTECTED) the instantiation is done. Often, such classes provide a public static method that creates an instance of this class and returns the reference to this instance to the caller. Such methods are sometimes called factory methods. Factory methods are executed when a instance of the class is created and has some advantages as compared to the instance constructor. Some advantages of factory methods are as follows: A factory method can have coding that executes before the actual instantiation.



For example, the method can perform checks, read data from the database, or set locks, before actually creating the instance. If an error occurs, no instance is created; and, no memory is allocated for it. ●

Classes can have more than one factory method. Each of the methods can have a different implementation and signature as well. The different factory method makes it possible to create instances of the same class based on different information. For example, one factory method creates a new instance that offers input parameters for all attributes, while another factory method only imports key information and then retrieve the other attribute values from the database.

354

© Copyright . All rights reserved.

Lesson: Implementing the Singleton Pattern



Use factory methods to administrate the instances of a class within the class itself. The administration of the instance within the class is often used to avoid the creation of many identical instances. A reference of every new instance is stored in a private static attribute of the class (an internal table). Whenever the factory method is called, it first checks whether an instance with this key already exists. If so, it returns the existing instance instead of creating a new one.



Use a factory method to instantiate one of the subclasses rather than the class itself. As an example, the factory method of an airplane class can check the plane type, then instantiate either a cargo or a passenger plane.

Example for a Class with Factory Method

Figure 139: Example for a Class with Factory Method

The example illustrates a class with a Factory Method and using a static attribute to reference all its instances. The instantiation is restricted to the class and is only done in static method FACTORY. When the method is called, the factory method checks whether an identical instance has already been created. If so, it returns the existing instance instead of creating a new one.

Hint: In this example, it is not necessary to make attributes public for the READ TABLE statement. As the factory method lies within the class, it has full access to all private attributes.

© Copyright . All rights reserved.

355

Unit 8: Object-Oriented Design Patterns

The Singleton Pattern

Figure 140: Singleton Class - Using a Factory Method

Use the singleton concept to prevent a class from being instantiated more than once for the same program context. There are various different ways to implement a singleton class. The first singleton pattern is a special case of the factory concept. Instead of storing several instances, the class stores only one instance. When the factory method GET_INSTANCE is called for the first time, it instantiates the class. For every subsequent call, it returns the reference to the existing object.

356

© Copyright . All rights reserved.

Lesson: Implementing the Singleton Pattern

Singleton Class - Using the Static Constructor

Figure 141: Singleton Class - Using the Static Constructor

The class uses its static constructor to create the single instance in advance. The GET_INSTANCE method does not create the instance but only returns a reference to the already existing instance. Hint: In a third variant of the singleton pattern, the GO_INSTANCE static attribute is made public and read-only. The GET_INSTANCE method is not required.

© Copyright . All rights reserved.

357

Unit 8: Object-Oriented Design Patterns

358

© Copyright . All rights reserved.

Unit 8 Exercise 21 Implement the Singleton Pattern

Business Example To improve the robustness of your application, you need to create two kinds of airplanes (passenger and cargo), implement them as final classes so they are not further specialized. Only specific airplanes are created and the travel agency can only be instantiated once. Template: SAPBC401_GCL_S2 Solution: SAPBC401_SPC_S1 Task 1 Use  the techniques of ABAP Objects to avoid the further specialization of passenger and cargo planes. 1. Complete your ZBC401_##_MAIN program or copy the template program. 2. Declare classes LCL_PASSENGER_PLANE and LCL_CARGO_PLANE as FINAL class. 3. What happens if you declare class LCL_AIRPLANE as FINAL class ?

4. What would happen if you make method DISPLAY_ATTRIBUTES in class LCL_AIRPLANE as final method?

Task 2 Use the techniques of ABAP Objects to inhibit the instantiation of class LCL_AIRPLANE. 1. Declare LCL_AIRPLANE as an abstract class. 2. Prove that it is not allowed to instantiate the class itself. In your main program, declare a reference variable TYPE REF TO lcl_airplane and implement a CREATE OBJECT statement for it. After the syntax check, remove the CREATE OBJECT statement. Task 3

© Copyright . All rights reserved.

359

Unit 8: Object-Oriented Design Patterns

Make sure the LCL_TRAVEL_AGENCY class can only be instantiated once in your program. Implement one of the singleton patterns discussed in the course. 1. Restrict the visibility of the instance constructor and inhibit any inheritance from the class. 2. Define a static attribute to store a reference to the one instance there. Depending on the pattern you implement, make it private or public and read-only. 3. Depending on the pattern you implement, define and implement a static constructor and/or a GET_INSTANCE method. Implement the instantiation of the class according to the singleton pattern. 4. Adjust the main program. Remove the CREATE OBJECT statement for the travel agency from the main program. Depending on the single pattern you implemented, replace it with a call of the GET_INSTANCE method or with an access to the public attribute. 5. Optional-If you have implemented a pattern that includes a GET_INSTANCE method, use a method chain to retrieve the singleton instance and call its DISPLAY_ATTRIBUTE method in one statement.

360

© Copyright . All rights reserved.

Unit 8 Solution 21 Implement the Singleton Pattern

Business Example To improve the robustness of your application, you need to create two kinds of airplanes (passenger and cargo), implement them as final classes so they are not further specialized. Only specific airplanes are created and the travel agency can only be instantiated once. Template: SAPBC401_GCL_S2 Solution: SAPBC401_SPC_S1 Task 1 Use  the techniques of ABAP Objects to avoid the further specialization of passenger and cargo planes. 1. Complete your ZBC401_##_MAIN program or copy the template program. a) Carry out this step in the usual manner. Additional information is available in the SAP Library. 2. Declare classes LCL_PASSENGER_PLANE and LCL_CARGO_PLANE as FINAL class. a) Refer the source code extract from the model solution. 3. What happens if you declare class LCL_AIRPLANE as FINAL class ? This results in a syntax error as classes LCL_CARGO_PLANE and LCL_PASSENGER_PLANE already inherited from this class. 4. What would happen if you make method DISPLAY_ATTRIBUTES in class LCL_AIRPLANE as final method? This results in a syntax error as the method is already redefined in classes LCL_CARGO_PLANE and LCL_PASSENGER_PLANE.

Task 2 Use the techniques of ABAP Objects to inhibit the instantiation of class LCL_AIRPLANE. 1. Declare LCL_AIRPLANE as an abstract class. a) Refer the source code extract from the model solution.

© Copyright . All rights reserved.

361

Unit 8: Object-Oriented Design Patterns

2. Prove that it is not allowed to instantiate the class itself. In your main program, declare a reference variable TYPE REF TO lcl_airplane and implement a CREATE OBJECT statement for it. After the syntax check, remove the CREATE OBJECT statement. a) Carry out this step in the usual manner. Task 3 Make sure the LCL_TRAVEL_AGENCY class can only be instantiated once in your program. Implement one of the singleton patterns discussed in the course. 1. Restrict the visibility of the instance constructor and inhibit any inheritance from the class. a) Use the FINAL and CREATE PRIVATE additions to the CLASS ... DEFINITION statement. Optionally, move the definition of the instance constructor to the private section. Refer the source code extract from the model solution. 2. Define a static attribute to store a reference to the one instance there. Depending on the pattern you implement, make it private or public and read-only. a) Refer the source code extract from the model solution. 3. Depending on the pattern you implement, define and implement a static constructor and/or a GET_INSTANCE method. Implement the instantiation of the class according to the singleton pattern. a) See the source code extract from the model solution. 4. Adjust the main program. Remove the CREATE OBJECT statement for the travel agency from the main program. Depending on the single pattern you implemented, replace it with a call of the GET_INSTANCE method or with an access to the public attribute. a) See the source code extract from the model solution. 5. Optional-If you have implemented a pattern that includes a GET_INSTANCE method, use a method chain to retrieve the singleton instance and call its DISPLAY_ATTRIBUTE method in one statement. a) Refer the source code extract from the model solution. Include BC401_SPC_S1_CARRIER *------------------------------------------------* * CLASS lcl_airplane DEFINITION *------------------------------------------------* CLASS lcl_airplane DEFINITION ABSTRACT. ... ENDCLASS. "lcl_airplane DEFINITION *------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. ... ENDCLASS. "lcl_airplane IMPLEMENTATION *------------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *------------------------------------------------*

362

© Copyright . All rights reserved.

Lesson: Implementing the Singleton Pattern

CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane FINAL. ... ENDCLASS. "lcl_cargo_plane DEFINITION *------------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *------------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. ... ENDCLASS. "lcl_cargo_plane IMPLEMENTATION *------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane FINAL. ... ENDCLASS. "lcl_passenger_plane DEFINITION *------------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *------------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. ... ENDCLASS. "lcl_passenger_plane IMPLEMENTATION Include BC401_SPC_S1_AGENCY *-------------------------------------------------* * CLASS lcl_travel_agency DEFINITION *-------------------------------------------------* CLASS lcl_travel_agency DEFINITION FINAL CREATE PRIVATE. PUBLIC SECTION. CLASS-METHODS: get_instance RETURNING value(ro_instance) TYPE REF TO lcl_travel_agency. METHODS: display_agency_partners, display_attributes. PRIVATE SECTION. DATA: mv_name TYPE string, mt_partners TYPE TABLE OF REF TO if_partner. CLASS-DATA: go_instance TYPE REF TO lcl_travel_agency. METHODS: constructor IMPORTING iv_name TYPE string. METHODS:

© Copyright . All rights reserved.

363

Unit 8: Object-Oriented Design Patterns

on_partner_created FOR EVENT partner_created OF if_partner IMPORTING sender. ENDCLASS.

"lcl_travel_agency DEFINITION

*---------------------------------------------------* * CLASS lcl_travel_agency IMPLEMENTATION *---------------------------------------------------* CLASS lcl_travel_agency IMPLEMENTATION. METHOD get_instance. IF go_instance IS NOT BOUND. CREATE OBJECT go_instance EXPORTING iv_name = 'Travel&Smile Travel'. ENDIF. ro_instance = go_instance. ENDMETHOD. "get_instance METHOD display_attributes. WRITE: / icon_private_files AS ICON, 'Travel Agency:'(007), mv_name. SKIP. display_agency_partners( ). ENDMETHOD. "display_attributes METHOD display_agency_partners. DATA: lo_partner TYPE REF TO if_partner. WRITE 'Here are the partners of the travel agency:'(008). ULINE. LOOP AT mt_partners INTO lo_partner. lo_partner->display_partner( ). ENDLOOP. ENDMETHOD. "display_agency_partners METHOD constructor. mv_name = iv_name. SET HANDLER on_partner_created FOR ALL INSTANCES. ENDMETHOD. "constructor METHOD on_partner_created. APPEND sender TO mt_partners. ENDMETHOD. "on_partner_created ENDCLASS. Main Program SAPBC401_SPC_S1 REPORT

sapbc401_spc_s1.

TYPE-POOLS icon. INCLUDE bc401_spc_s1_agency. INCLUDE bc401_spc_s1_carrier. INCLUDE bc401_spc_s1_rental.

364

© Copyright . All rights reserved.

Lesson: Implementing the Singleton Pattern

DATA: go_hotel go_agency go_vehicle go_truck go_bus go_rental go_passenger go_cargo go_carrier

TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE

REF REF REF REF REF REF REF REF REF

TO TO TO TO TO TO TO TO TO

cl_hotel2, lcl_travel_agency, lcl_vehicle, lcl_truck, lcl_bus, lcl_rental, lcl_passenger_plane, lcl_cargo_plane, lcl_carrier.

START-OF-SELECTION. ******************* ******* create travel_agency *********************** * CREATE OBJECT go_agency * EXPORTING * iv_name = 'Travel&Smile Travel'. go_agency = lcl_travel_agency=>get_instance( ). ******* create hotel ******************************* CREATE OBJECT go_hotel EXPORTING iv_name = 'Sleep Well Hotel' iv_beds = 345. ******* create rental ******************************* CREATE OBJECT go_rental EXPORTING iv_name = 'Happy Car Rental'. ******* create truck ********************************* CREATE OBJECT go_truck EXPORTING iv_make = 'MAN' iv_cargo = 45. ******* create truck ********************************* CREATE OBJECT go_bus EXPORTING iv_make = 'Mercedes' iv_passengers = 80. ******* create truck ********************************* CREATE OBJECT go_truck EXPORTING iv_make = 'VOLVO' iv_cargo = 48. ***** Create Carrier ********************************* CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly Travel'. ***** Passenger Plane ********************************

© Copyright . All rights reserved.

365

Unit 8: Object-Oriented Design Patterns

CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ***** cargo Plane ************************************ CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ***** show attributes of all partners of travel_agency go_agency->display_attributes( ). * Optional part: Use method chain: * * lcl_travel_agency=>get_instance( )->display_attributes( ).

366

© Copyright . All rights reserved.

Lesson: Implementing the Singleton Pattern

LESSON SUMMARY You should now be able to: ●

Implement factory methods



Implement the singleton pattern

© Copyright . All rights reserved.

367

Unit 8 Lesson 3 Implementing Factory Classes Using Friendship

LESSON OVERVIEW This lesson explains the method of implementing factory classes using friendship. Business Example As a developer, create classes for an airplane using friendship. For this reason, you require the following knowledge: ●

An understanding of the definition of friendship relationships



An understanding of friendship and inheritance



An understanding of the implementation of factory classes

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Implement friendship relationships

Definition of Friendship Relationships

Figure 142: Definition of a Friendship Relationship Between Classes

368

© Copyright . All rights reserved.

Lesson: Implementing Factory Classes Using Friendship

In some cases, classes have to work together so closely that one class needs access to the other classes protected and private components. Similarly, one class might need to be able to create instances of the other class regardless of the visibility of the constructor. To avoid making these options available to all users of the class, use the concept of class friendship. A class can grant friendship to other classes and interfaces and, hence, to all classes that implement the interface. To create friendship, use the FRIENDS addition of the CLASS statement or the FRIENDS tab in the Class Builder. All classes and interfaces to which friendship is granted are listed there. Granting friendship is one direction. A class granting friendship is not automatically a friend of the classes’ friends. If a class granting friendship wants to access the non-public components of a friend, this friend must also explicitly grant friendship to it.

Implementation of Factory Classes

Figure 143: Example of a Factory Class

A typical application of the friends concept is the definition of a factory class. Like the factory method, a factory class creates and administrates the instances of a class. By outsourcing the administration to a dedicated class, the class itself is kept smaller and easier to understand. In the example, LCL_FACTORYserves as a factory class for airplanes. LCL_FACTORY class provides a public method CREATE_AIRPLANE in which CREATE_AIRPLANE either instantiates class LCL_AIRPLANE or returns a reference to an already existing instance. To restrict the instantiation, class LCL_AIRPLANE is defined with addition CREATE PRIVATE. By adding FRIENDS LCL_FACTORY, the friendship allows the factory class and only the factory class to create airplane instances and to access the private attributes.

© Copyright . All rights reserved.

369

Unit 8: Object-Oriented Design Patterns

Hint: Another advantage of the dedicated factory class is that if the class has subclasses, the decision on which of the classes should be instantiated could be done inside the factory class rather than by the calling program. In the example, the CREATE_AIRPLANE method could create and return an instance of either LCL_CARGO_PLANE or LCL_PASSENGER_PLANE depending on the plane type.

Friendship and Inheritance The friend attribute is inherited. Classes that inherit from friends and interfaces containing a friend as a component interface, also become friends. Therefore, advise that extreme caution must be taken when granting friendship. The higher up a friend is in the inheritance tree, the more subclasses can access all components of a class that grants friendship. Conversely, granting friendship is not inherited. A friend of a superclass is, therefore, not automatically a friend of its subclasses.

370

© Copyright . All rights reserved.

Unit 8 Exercise 22 Implement a Factory Class Using Friendship

Business Example Instead of instantiating airplane objects in the main program directly, create airplanes by using a factory class. The factory class should provide one single factory method. Depending on the input, the factory class decides inside this factory method, whether to create a cargo plane or a passenger plane. Template: SAPBC401_SPC_S1 Solution: SAPBC401_ SPC_S2 Task 1 In your program, define a factory class (suggested name: LCL_AIRPLANE_FACTORY) with a public static factory method for airplanes (suggested name: CREATE_AIRPLANE). The factory method should have suitably typed import parameters for name, plane type, cargo, and seats. The factory method for import parameters cargo and seats can be optional. It should also have a single returning parameter to return a reference to an airplane instance – either a cargo plane or a passenger plane. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number), or copy the template program. 2. Edit the include, which contains the classes for airplanes. Add the definition of the new class there. 3. Within the class, define a public static factory method for airplanes. Define four import parameters for name, plane type, cargo, and seats. Name and type them exactly as in the constructors of your airplane classes. Make the parameters for cargo and seats optional. Hint: Use addition OPTIONAL to do so.

4. Define a returning parameter (suggested name: RO_AIRPLANE). How do you have to type the parameter so that the method can return a reference to either a cargo plane instance or a passenger plane instance?

Task 2

© Copyright . All rights reserved.

371

Unit 8: Object-Oriented Design Patterns

Implement the factory method. Depending on the optional parameter that is supplied, create either a cargo plane instance or a passenger plane instance. Define a suitable exception and raise it if both optional parameters are supplied or none of them. 1. In the factory method, define two local reference variables. Type one with the class for cargo planes (LCL_CARGO_PLANE) and one with the class for passenger planes (LCL_PASSENGER_PLANE). 2. Implement an IF-structure in which you analyze the content of the import parameters for cargo and seats. Create either an instance of the cargo plane class or the passenger plane class. In the case of success, move the reference to the new object to the returning parameter. 3. In the definition of the factory class, add two exceptions. One that you raise if a wrong plane type was specified (suggested name: WRONG_PLANETYPE), and one that you raise if both or none of the optional parameters were supplied (suggested name: WRONG_PARAM_COMBINATION). Task 3 Restrict the creation of cargo planes and passenger planes so that they can only be created from inside the factory class. 1. Use the CREATE PRIVATE addition to restrict the instantiation of the classes for cargo planes and passenger planes. Optionally, move the constructor definitions of both classes to the private section. 2. Use the FRIENDS addition to allow the instantiation of the classes for cargo planes and passenger planes from inside the factory class. Hint: You have to use statement CLASS... DEFINITION DEFERRED  before the definition of the airplane classes. Otherwise, the factory class or at least its name, is not known to the syntax check when it reaches the FRIENDS addition.

Task 4 Adjust your main program. Remove the direct instantiations of airplanes and replace them by calls of the factory method. 1. Replace the instantiations of airplanes with calls of the factory method. Hint: If you have used exactly the same parameter names as in the constructors, you can keep the parameter passing.

372

© Copyright . All rights reserved.

Lesson: Implementing Factory Classes Using Friendship

2. Do you have to actually receive the references to the new objects?

3. Activate, test, and debug your program.

© Copyright . All rights reserved.

373

Unit 8 Solution 22 Implement a Factory Class Using Friendship

Business Example Instead of instantiating airplane objects in the main program directly, create airplanes by using a factory class. The factory class should provide one single factory method. Depending on the input, the factory class decides inside this factory method, whether to create a cargo plane or a passenger plane. Template: SAPBC401_SPC_S1 Solution: SAPBC401_ SPC_S2 Task 1 In your program, define a factory class (suggested name: LCL_AIRPLANE_FACTORY) with a public static factory method for airplanes (suggested name: CREATE_AIRPLANE). The factory method should have suitably typed import parameters for name, plane type, cargo, and seats. The factory method for import parameters cargo and seats can be optional. It should also have a single returning parameter to return a reference to an airplane instance – either a cargo plane or a passenger plane. 1. Complete your program ZBC401_##_MAIN (where ## is your two-digit group number), or copy the template program. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. 2. Edit the include, which contains the classes for airplanes. Add the definition of the new class there. a) Refer the source text excerpt from the model solution. 3. Within the class, define a public static factory method for airplanes. Define four import parameters for name, plane type, cargo, and seats. Name and type them exactly as in the constructors of your airplane classes. Make the parameters for cargo and seats optional. Hint: Use addition OPTIONAL to do so.

a) Refer the source text excerpt from the model solution.

374

© Copyright . All rights reserved.

Lesson: Implementing Factory Classes Using Friendship

4. Define a returning parameter (suggested name: RO_AIRPLANE). How do you have to type the parameter so that the method can return a reference to either a cargo plane instance or a passenger plane instance? a) You have to type the parameter with the common superclass of cargo planes and passenger planes, that is, TYPE REF TO lcl_airplane. Refer the source text excerpt from the model solution.

Task 2 Implement the factory method. Depending on the optional parameter that is supplied, create either a cargo plane instance or a passenger plane instance. Define a suitable exception and raise it if both optional parameters are supplied or none of them. 1. In the factory method, define two local reference variables. Type one with the class for cargo planes (LCL_CARGO_PLANE) and one with the class for passenger planes (LCL_PASSENGER_PLANE). a) Refer the source text excerpt from the model solution. 2. Implement an IF-structure in which you analyze the content of the import parameters for cargo and seats. Create either an instance of the cargo plane class or the passenger plane class. In the case of success, move the reference to the new object to the returning parameter. a) Refer the source text excerpt from the model solution. 3. In the definition of the factory class, add two exceptions. One that you raise if a wrong plane type was specified (suggested name: WRONG_PLANETYPE), and one that you raise if both or none of the optional parameters were supplied (suggested name: WRONG_PARAM_COMBINATION). a) Refer the source text excerpt from the model solution. Task 3 Restrict the creation of cargo planes and passenger planes so that they can only be created from inside the factory class. 1. Use the CREATE PRIVATE addition to restrict the instantiation of the classes for cargo planes and passenger planes. Optionally, move the constructor definitions of both classes to the private section. a) Refer the source text excerpt from the model solution. 2. Use the FRIENDS addition to allow the instantiation of the classes for cargo planes and passenger planes from inside the factory class. Hint: You have to use statement CLASS... DEFINITION DEFERRED  before the definition of the airplane classes. Otherwise, the factory class or at least its name, is not known to the syntax check when it reaches the FRIENDS addition.

© Copyright . All rights reserved.

375

Unit 8: Object-Oriented Design Patterns

a) Refer the source text excerpt from the model solution. Task 4 Adjust your main program. Remove the direct instantiations of airplanes and replace them by calls of the factory method. 1. Replace the instantiations of airplanes with calls of the factory method. Hint: If you have used exactly the same parameter names as in the constructors, you can keep the parameter passing. a) Refer the source text excerpt from the model solution. 2. Do you have to actually receive the references to the new objects? No. Through the message handling implemented earlier, the carrier instance takes care of all new airplane instances and aggregates them. 3. Activate, test, and debug your program. a) Carry out this step in the usual manner. For more information, refer to the SAP Library. Include BC401_SPC_S2_CARRIER CLASS lcl_airplane_factory DEFINITION DEFERRED. *----------------------------------------------------* * CLASS lcl_airplane DEFINITION * *----------------------------------------------------* CLASS lcl_airplane DEFINITION ABSTRACT. ... ENDCLASS. "lcl_airplane DEFINITION *-----------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION * *-----------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. ... ENDCLASS. "lcl_airplane IMPLEMENTATION *-----------------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *-----------------------------------------------------* * *-----------------------------------------------------* CLASS lcl_cargo_plane DEFINITION

376

© Copyright . All rights reserved.

Lesson: Implementing Factory Classes Using Friendship

INHERITING FROM lcl_airplane FINAL CREATE PRIVATE FRIENDS lcl_airplane_factory. ... ENDCLASS. "lcl_cargo_plane DEFINITION *-----------------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *-----------------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. ... ENDCLASS. "lcl_cargo_plane IMPLEMENTATION *-----------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *-----------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane FINAL CREATE PRIVATE FRIENDS lcl_airplane_factory. ... ENDCLASS. "lcl_passenger_plane DEFINITION *---------------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *---------------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. ... ENDCLASS. "lcl_passenger_plane IMPLEMENTATION *--------------------------------------------------* * CLASS lcl_carrier DEFINITION *--------------------------------------------------* CLASS lcl_carrier DEFINITION. ... ENDCLASS. "lcl_carrier DEFINITION *--------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *--------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. ... ENDCLASS.

"lcl_carrier IMPLEMENTATION

*--------------------------------------------------* * CLASS lcl_airplane_factory DEFINITION *--------------------------------------------------* CLASS lcl_airplane_factory DEFINITION. PUBLIC SECTION.

© Copyright . All rights reserved.

377

Unit 8: Object-Oriented Design Patterns

CLASS-METHODS: create_airplane IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype iv_cargo TYPE s_plan_car OPTIONAL iv_seats TYPE s_seatsmax OPTIONAL RETURNING value(ro_airplane) TYPE REF TO lcl_airplane EXCEPTIONS wrong_planetype wrong_param_combination. ENDCLASS. "lcl_airplane_factory DEFINITION *--------------------------------------------------* * CLASS lcl_airplane_factory IMPLEMENTATION *--------------------------------------------------* CLASS lcl_airplane_factory IMPLEMENTATION. METHOD create_airplane. DATA: lo_cargo TYPE REF TO lcl_cargo_plane, lo_passenger TYPE REF TO lcl_passenger_plane. IF iv_cargo IS NOT INITIAL AND iv_seats IS INITIAL. CREATE OBJECT lo_cargo EXPORTING iv_name = iv_name iv_planetype = iv_planetype iv_cargo = iv_cargo EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. RAISE wrong_planetype. ELSE. ro_airplane = lo_cargo. ENDIF. ELSEIF iv_cargo IS INITIAL AND iv_seats IS NOT INITIAL. CREATE OBJECT lo_passenger EXPORTING iv_name = iv_name iv_planetype = iv_planetype iv_seats = iv_seats EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. RAISE wrong_planetype. ELSE. ro_airplane = lo_passenger. ENDIF. ELSE. RAISE wrong_param_combination. ENDIF.

378

© Copyright . All rights reserved.

Lesson: Implementing Factory Classes Using Friendship

ENDMETHOD. ENDCLASS.

"create_airplane "lcl_airplane_factory IMPLEMENTATION SAPBC401_SPC_S2

REPORT

sapbc401_spc_s2.

TYPE-POOLS icon. INCLUDE bc401_spc_s2_agency. INCLUDE bc401_spc_s2_carrier. INCLUDE bc401_spc_s2_rental. DATA: go_agency TYPE REF TO lcl_travel_agency, go_hotel TYPE REF TO cl_hotel2, go_vehicle TYPE REF TO lcl_vehicle, go_truck TYPE REF TO lcl_truck, go_bus TYPE REF TO lcl_bus, go_rental TYPE REF TO lcl_rental, *go_passenger TYPE REF TO lcl_passenger_plane, *go_cargo TYPE REF TO lcl_cargo_plane, go_carrier TYPE REF TO lcl_carrier. START-OF-SELECTION. ******************* ******* create travel_agency *********************** * CREATE OBJECT go_agency * EXPORTING * iv_name = 'Travel&Smile Travel'. go_agency = lcl_travel_agency=>get_instance( ). ******* create hotel ******************************* CREATE OBJECT go_hotel EXPORTING iv_name = 'Sleep Well Hotel' iv_beds = 345. ******* create rental ****************************** CREATE OBJECT go_rental EXPORTING iv_name = 'Happy Car Rental'. ******* create truck ******************************* CREATE OBJECT go_truck EXPORTING iv_make = 'MAN' iv_cargo = 45. ******* create truck ******************************* CREATE OBJECT go_bus EXPORTING iv_make = 'Mercedes' iv_passengers = 80.

© Copyright . All rights reserved.

379

Unit 8: Object-Oriented Design Patterns

******* create truck ******************************* CREATE OBJECT go_truck EXPORTING iv_make = 'VOLVO' iv_cargo = 48. ***** Create Carrier ******************************* CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly-Travel'. ***** Passenger Plane ****************************** lcl_airplane_factory=>create_airplane( EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1 wrong_param_combination = 2 ). IF sy-subrc = 1. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ***** cargo Plane ********************************** lcl_airplane_factory=>create_airplane( EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1 wrong_param_combination = 2 ). IF sy-subrc = 1. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF. ***** show attributes of all partners of travel_agency go_agency->display_attributes( ).

380

© Copyright . All rights reserved.

Lesson: Implementing Factory Classes Using Friendship

LESSON SUMMARY You should now be able to: ●

Implement friendship relationships

© Copyright . All rights reserved.

381

Unit 8: Object-Oriented Design Patterns

382

© Copyright . All rights reserved.

Unit 8 Learning Assessment

1. Static _____________ cannot be abstract because they cannot be redefined. Choose the correct answer. X

A classes

X

B structures

X

C methods

X

D attributes

2. You can prevent a class from being inherited by using the final addition with the class statement. Determine whether this statement is true or false. X

True

X

False

3. By making the key attributes __________, we can avoid the redundant storage of information. Choose the correct answer. X

A public

X

B private

X

C protected

4. An association means that at runtime an instance of one class stores references to objects of another class. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

383

Unit 8: Learning Assessment

5. If the instance constructor is protected, the visibility is extended to all of its subclasses. Determine whether this statement is true or false. X

True

X

False

6.  Which of the following are the advantages of factory method? Choose the correct answers. X

A A factory method can have coding that is executed before the actual instantiation.

X

B A class can have more than one factory method with different implementation and signature.

X

C Factory methods cannot be used to administrate the instances of a class within the class itself.

X

D A factory method cannot be used to instantiate one of the subclasses rather than the class itself.

7. Which of the following is done using the singleton concept? Choose the correct answers. X

A Preventing a class from being instantiated more than once for the same program context

X

B Restricting the visibility of the instance constructor

X

C Keeping a reference to all its instances in a static attribute

X

D Storing only one instance instead of storing several instances

8. Which of the following concepts is used to provide a class access to the private components of the other class? Choose the correct answer.

384

X

A Singleton

X

B Friendship

X

C Interface

X

D Casting

© Copyright . All rights reserved.

Unit 8 Learning Assessment - Answers

1. Static _____________ cannot be abstract because they cannot be redefined. Choose the correct answer. X

A classes

X

B structures

X

C methods

X

D attributes

2. You can prevent a class from being inherited by using the final addition with the class statement. Determine whether this statement is true or false. X

True

X

False

3. By making the key attributes __________, we can avoid the redundant storage of information. Choose the correct answer. X

A public

X

B private

X

C protected

4. An association means that at runtime an instance of one class stores references to objects of another class. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

385

Unit 8: Learning Assessment - Answers

5. If the instance constructor is protected, the visibility is extended to all of its subclasses. Determine whether this statement is true or false. X

True

X

False

6.  Which of the following are the advantages of factory method? Choose the correct answers. X

A A factory method can have coding that is executed before the actual instantiation.

X

B A class can have more than one factory method with different implementation and signature.

X

C Factory methods cannot be used to administrate the instances of a class within the class itself.

X

D A factory method cannot be used to instantiate one of the subclasses rather than the class itself.

7. Which of the following is done using the singleton concept? Choose the correct answers. X

A Preventing a class from being instantiated more than once for the same program context

X

B Restricting the visibility of the instance constructor

X

C Keeping a reference to all its instances in a static attribute

X

D Storing only one instance instead of storing several instances

8. Which of the following concepts is used to provide a class access to the private components of the other class? Choose the correct answer.

386

X

A Singleton

X

B Friendship

X

C Interface

X

D Casting

© Copyright . All rights reserved.

UNIT 9

Object-Oriented Exception Handling

Lesson 1 Explaining Class-Based Exception Handling

388

Lesson 2 Defining and Raising Exceptions Exercise 23: Implement Class-Based Exceptions

395 403

Lesson 3 Implementing Advanced Exception Handling Techniques Exercise 24: Map Exceptions to Each Other

418 427

UNIT OBJECTIVES ●

Explain class-based exceptions



Handle class-based exceptions



Debug class-based exceptions



Define global exception classes



Raise class-based exceptions



Propagate exceptions



Explain the hierarchy of predefined exception classes



Explain different ways of handling an exception



Retry after exceptions



Implement resumable exceptions



Reraise exceptions



Map exceptions to each other

© Copyright . All rights reserved.

387

Unit 9 Lesson 1 Explaining Class-Based Exception Handling

LESSON OVERVIEW This lesson explains how to handle and debug class-based exceptions. Business Example You must use the new exceptions concept in your ABAP Object programs. For this reason, you require the following knowledge: ●

An understanding of class-based exceptions



An understanding of how to handle class-based exceptions



An understanding of how to debug class-based exceptions

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Explain class-based exceptions



Handle class-based exceptions



Debug class-based exceptions

Class-Based Exceptions An exception is a situation that arises while a program is being executed during which there is no point to continue the normal program flow. SAP Web AS 6.10 introduced a new ABAP Objects exception concept that exists parallel to the existing concept based on sy-subrc. Exceptions and exception handling are now based on classes. This new ABAP Objects exception concept enhanced the classic way of handling exception using sy-subrc.

Hint: Note that the use of class-based exceptions is not limited to object-oriented contexts. Class-based exceptions can be raised and handled in all processing blocks. In particular, all previously catchable runtime errors can be handled as class-based exceptions.

388

© Copyright . All rights reserved.

Lesson: Explaining Class-Based Exception Handling

Figure 144: An Overview of the Class-Based Exception Concept

In the new exception concept, an exception is represented by an exception object. An exception object is an instance of an exception class. The attribute values of the exception object contain information about the respective error situation. Raising a class-based exception normally means instantiating an exception class and setting the attributes. Handling a class-based exception involves evaluating the exception object and its attribute values. The program needs to raise and handle the exceptions. Class-based exceptions are raised either by the RAISE EXCEPTION statement or by the runtime environment. You catch and handle class-based exceptions with the TRY...CATCH...ENDTRY structure.

© Copyright . All rights reserved.

389

Unit 9: Object-Oriented Exception Handling

Hierarchy of Exception Classes

Figure 145: Exception Classes – The Inheritance Hierarchy

You can define your own exception classes, but the system already includes a range of predefined exception classes – particularly for exceptions in the runtime environment. You usually create exception classes globally in the Class Builder, but you can also define local exception classes within a program or global class. The names of global exception classes always start with CX_. Those global exception classes that the runtime environment uses start with CX_SY_. SAP recommendeds that you start the names of local exception classes with LCX_. All exception classes are derived from one exception class, CX_ROOT. Therefore, you can generically access any exception object through a reference variable, REF TO CX_ROOT. However, a new exception class is not allowed to inherit directly from CX_ROOT. You must derive any new exception class directly or indirectly from one of the subclasses CX_ROOT CX_NO_CHECK, CX_DYNAMIC_CHECK, or CX_STATIC_CHECK. Through this, all exception classes are subdivided into three groups. Depending on the group to which a given exception belongs, the exception is treated differently by syntax check and runtime environment. The default group is CX_STATIC_CHECK, which ensures maximum syntax check and program stability. The other groups must only be used in special cases. The GET_SOURCE_POSITION method returns the name of the main program or include program and also the line number in the source code where the exception occurs. The GET_TEXT method returns an exception text in the form of a string. This method is not defined in CX-ROOT directly but in interface IF_MESSAGE, which is implemented by CX-ROOT.

390

© Copyright . All rights reserved.

Lesson: Explaining Class-Based Exception Handling

TRY-ENDTRY Control Structure

Figure 146: Structure of a TRY-ENDTRY Block

You can handle an exception if the statement that raised it is enclosed inside a TRY-ENDTRY control structure. You handle the exception using the CATCH statement in the TRY-ENDTRY structure. The TRY block contains the statements for which the exceptions need to be handled. A CATCH block contains the exception handler which is executed if a specified exception has occurred in the associated TRY block. Like all control structures in ABAP Objects, you can nest TRY-ENDTRY structures to any depth. In particular, the TRY block, the CATCH block, and the CLEANUP block can contain complete TRYENDTRY structures themselves. Specify any number of exception classes in the CATCH statement. In this way, you define an exception handler for all these exception classes and their subclasses. If an exception occurs, the system searches for a matching CATCH statement in the TRYENDTRY structure that immediately surrounds the statement. It searches through the CATCH blocks for the relevant exception class  or the superclasses from the inheritance hierarchy.  If any of the relevant exception classes is found, the program navigates directly to the hander. If the TRY-ENDTRY block it does not find any exception class, the system gradually searches outwards in all the surrounding TRY-ENDTRY structures. If no handler can be found within the same procedure, the system tries to propagate the exception to the calling program. This process will be discussed in more detail later. If a TRY-ENDTRY structure contains a CLEANUP block, this block is executed when the TRYENDTRY structure is exited because the system cannot find a handler within the TRY-ENDTRY structure itself but instead in a surrounding TRY-ENDTRY structure or in a calling program.

© Copyright . All rights reserved.

391

Unit 9: Object-Oriented Exception Handling

Example Syntax for Handling Predefined Exceptions

Figure 147: Example Syntax for Handling Predefined Exceptions

The figure shows an example of syntax for handling predefined exceptions. To analyze the exception object in an exception handler, use the CATCH statement in the form CATCH ... INTO ... You have to specify a suitably typed object reference after the optional addition INTO. The reference can be a reference either to the exception class itself or to any of its superclasses. Just before the system executes CATCH block, the system fills the reference variable so that it points to the exception object describing the present error situation. If the value range for data type I is exceeded in the calculation, the runtime system raises exception CX_SY_ARITHMETIC_OVERFLOW. This exception is handled in the implemented CATCH block. The reference to the appropriate instance is stored in data object GO_EXC in the example. The handler can access the instance’s exception text using the functional method GET_TEXT. The exception text is stored in the data object GV_TEXT with the type STRING and then displayed as an information message. You can handle any other public component of the exception object during exception handling depending on the static type of the reference variable. In the example above, the reference variable is typed as REF TO CX_ROOT, which restricts access to those components defined in CX_ROOT. To access the more-specific components of the exception object, you need a morespecific type reference variable type. You can also use the superclass CX_SY_ARITHMETIC_ERROR and the super-superclass CX_DYNAMIC_CHECK to access the specific components of the exception object. The ABAP keyword documentation for each statement lists the classes whose exceptions may occur when that statement is executed.

392

© Copyright . All rights reserved.

Lesson: Explaining Class-Based Exception Handling

Analysis of Class-Based Exceptions in the Debugger

Figure 148: Class-Based Exceptions in Debugging Mode

If an exception is raised, the system displays name of the exception class in the Exception Raised field in debugging mode. If a CATCH block catches the exception a success message displays. The pointer for the current statement then moves to this CATCH block. Two pushbuttons appear if an exception occurrs. Use the pushbuttons to analyze the exception object and to navigate to the point in the source code where the exception occurred respectively.

Hint: For debugger runtime performance reasons, the system does not actually create exception objects if the INTO addition is missing from the respective CATCH statement. In such cases, the Last Exception Object pushbutton normally does not appear. To set the ABAP Debugger to always create the exception object, choose the respective option in the debugger settings.

LESSON SUMMARY You should now be able to: ●

Explain class-based exceptions



Handle class-based exceptions

© Copyright . All rights reserved.

393

Unit 9: Object-Oriented Exception Handling



394

Debug class-based exceptions

© Copyright . All rights reserved.

Unit 9 Lesson 2 Defining and Raising Exceptions

LESSON OVERVIEW This lesson explains how to define and raise global exception classes. Business Example You need to define global exception classes for your ABAP Object programs. For this reason, you require the following knowledge: ●

An understanding of the definition of global exception classes



An understanding of how to raise class-based exceptions



An understanding of how to implement exception propagation

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Define global exception classes



Raise class-based exceptions



Propagate exceptions

© Copyright . All rights reserved.

395

Unit 9: Object-Oriented Exception Handling

Definition of Global Exception Classes

Figure 149: Creating Global Exception Classes

You use Class Builder to create a global class as described in SAP Library. When you enter the name of global class, use the prefix CX_. Choose the Exception Class option as the class type.

Note: As of SAP NetWeaver Application Server 6.40 (SAP NW AS 6.40), you can still select the with Message Class checkbox when you create an exception class. You take the texts that should appear when exceptions occur from the messages classes identified in the message statement. You find these known messages and message classes in table T100. In releases before SAP NW AS 6.40, exception texts were stored solely in the Online Text Repository (OTR). When you create an exception class, do not change the default entry for Inherits from unless you are fully aware of the consequences of making the change.

Define additional attributes in your exception class as necessary (for example, for generic extensions to exception texts).

396

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

Hint: If such an attribute is public, the Class Builder automatically adjusts the instance constructor of the exception class. A new input parameter is generated and a value can be set for this attribute when raising the exception. The import parameter is generated with the same name as the attribute. By default, the parameter is optional. You may declare it mandatory by editing the constructor’s signature. Define Variable Exception Texts

Figure 150: Define Variable Exception Texts

Save as many exception texts as you need. When you save exception texts, you can insert attributes as parameters in the static text using the form &&.

Note: For the first text you create, always use a predefined static constant as an ID. The text always has the same name as the exception class itself. If you have not specified a text when the exception is raised, the system uses the text with this ID. You define other IDs for all other texts. Class Builder then generates identically named static constants automatically. When the exception is raised, pass one of these constants to import parameter TEXTID to specify the appropriate text for the exception instance.

© Copyright . All rights reserved.

397

Unit 9: Object-Oriented Exception Handling

Note: In releases before SAP NW AS 6.40, exception texts for global exception classes and their translations were stored in OTR. You can assign several texts to a single class. You assign a text to an exception using the TEXTID attribute, which contains the globally unique ID of the text object in OTR in an instance at run time. The GET_TEXT method then exports this text, replaces any text parameters with the contents of the relevant attributes as required, and returns the text as a character string. Activate the exception class after filling in the exception texts.

Raising of Class-Based Exceptions

Figure 151: Variants of Statement RAISE EXCEPTION

The figure shows an example for each variants of statement RAISE EXCEPTION. Raising class-based exceptions is done using the RAISE EXCEPTION statement. There are two variants of the statement. Variants of Statement RAISE EXCEPTION ... RAISE EXCEPTION TYPE [EXPORTING ...]. This statement creates a new exception object that is an instance of the class. RAISE EXCEPTION . This statement uses an existing exception object that the one points to. The exception object was either created directly using a CREATE OBJECT statement or caught in a previous CATCH ... INTO ...statement.

398

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

When using the first variant, it is possible to provide values for the constructor parameters using the EXPORTING addition. One of these parameters is used to set the exception text in the new exception object.

Set Exception Text

Figure 152: Setting the Exception Text

All exception classes offer an optional parameter TEXTID in their constructors. Use this parameter if more than one message text is available in the exception class and you do not want to raise the exception with the default text. For each text defined on the Texts tab, the Class Builder generates a public constant of the same name. Constants may also be inherited from the superclasses of the exception class. By default, the system raises an exception with the text that has the same name as the exception class. To raise the exception with another text, use the corresponding constant as the actual parameter for constructor parameter TEXTID.

Note: The type of the constants and parameter TEXTID in the constructor is determined by whether or not the exception class was created with the With message class flag. If the exception class still uses OTR texts, the constants are of type CHAR and contain a technical ID of the OTR text. If the exception class uses a message class, the constants are structures containing the name of the message class, the message number, and so on.

© Copyright . All rights reserved.

399

Unit 9: Object-Oriented Exception Handling

Exception Propagation

Figure 153: Propagating Class-Based Exceptions

You do not necessarily need to handle exceptions that occur in procedures where they occur. You can instead propagate exceptions to the caller of the procedure. The caller can then handle the exception or propagate it to its own caller, and so on. The highest levels to which an exception can be propagated are processing blocks without local data areas, that is, event blocks or dialog modules. You must deal with the exceptions propagated by the called procedures while you deal with any exceptions raised within the processing block itself. Otherwise, a runtime error occurs. To propagate an exception from a procedure, you generally use the RAISING addition when you define the procedure interface. In methods of local classes and subroutines, specify the RAISING addition directly when you are defining the procedure. For example: METHODS meth_name ... RAISING cx_... cx_... or FORM subr_name ... RAISING cx_... cx_.... In RAISING statement, list the exception classes whose instances are to be propagated. In methods of global classes, enter exception classes whose instances are to be propagated into the exception table of the method in the Class Builder. You also need to set the Exception Class flag for each exception table. The process is similar for function modules. To set the indicator in Function Builder, choose the Exceptions tab.

Hint: A single method, form, or function module can raise only one type of exception, that is, either class-based or conventional.

400

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

Propagating Exceptions Over Several Hierarchy – Levels

Figure 154: Propagating Exceptions Over Several Hierarchy – Levels

Propagation of class-based exception does not require that the calling method actually handles the exception. The caller may pass the exception to its own caller even without handling it. In the example, the constructor propagates the CX_EXC exception raised by the GET_TECH_ATTR method. When the error occurs and the program raises the excpetion, the program flow jumps directly to the CATCH block in the main program.

Note: If the constructor implements the optional CLEANUP block, the system executes this block is executed before the CATCH block of the main program.

© Copyright . All rights reserved.

401

Unit 9: Object-Oriented Exception Handling

402

© Copyright . All rights reserved.

Unit 9 Exercise 23 Implement Class-Based Exceptions

Business Example  Your program should use the class-based exception concept if an invalid plane type is provided when creating an airplane instance. Template: SAPBC401_GCL_S2 Solution: SAPBC401_EXC_S1 (Main program) CX_INVALID_PLANETYPE (exception class) Task 1 Create a global exception class for an invalid airplane type. 1. Create a global exception class called ZCX_##_INVALID_PLANETYPE (where ## is your twodigit group number). Set the syntax check to ensure that exceptions based on this class are either handled directly or propagated. Choose the superclass accordingly. In the exception class, use texts from a message class instead of freely defined texts. Hint: To state whether or not the messages from a message class are used when you create the exception class,select the Message Class checkbox. 2. Add an attribute for the airplane type (suggested name: PLANETYPE) and assign the type S_PLANETYPE to it. Make sure a corresponding parameter is defined in the signature of the constructor. Hint: You cannot define the constructor of an exception class directly. If you define the attribute as public, a corresponding import parameter is added to the constructor by the framework. 3. Create a default error message. Include a placeholder in the message text so that it can be enhanced dynamically to include the airplane type.

© Copyright . All rights reserved.

403

Unit 9: Object-Oriented Exception Handling

Hint: You can define your own message class and message or use message 020 from message class BC401.

Task 2 Raise the new exception in method GET_TECHNICAL ATTRIBUTES of your local class LCL_AIRPLANE. 1. Complete program ZBC401_##_MAIN or copy the template program. 2. Edit the definition of local class LCL_AIRPLANE. Remove the classical, non class-based exception WRONG_PLANETYPE from the signature of method GET_TECHNICAL_ATTRIBUTES and replace it with your new class-based exception ZCX_##_INVALID_PLANETYPE. 3. Edit the implementation of method GET_TECHNICAL_ATTRIBUTES and raise the class-based exception instead of the classical exception. Ensure that the wrong plane type value is handed over to the constructor and stored in the exception object. Task 3 Propagate the class-based exception explicitly through the entire call hierarchy so that you must handle it only once in the main program. 1. Edit the definition of local class LCL_AIRPLANE. Remove the classical, non class-based exception WRONG_PLANETYPE from the signature of method GET_TECHNICAL_ATTRIBUTES and replace it with your new class-based exception, ZCX_##_INVALID_PLANETYPE. 2. Edit the implementation of the constructor of local class LCL_AIRPLANE. While calling method GET_TECHNICAL_ATTRIBUTES, remove the handling of classical exception WRONG_PLANETYPE. 3. Why is it not necessary to handle the class-based exception ZCX_##_INVALID_PLANETYPE here?

4. Edit the definition of local class LCL_PASSENGER_PLANE. Remove the classical, non classbased exception WRONG_PLANETYPE from the signature of the CONSTRUCTOR method and replace it with your new class-based exception ZCX_##_INVALID_PLANETYPE. Edit the implementation of the constructor of local class LCL_PASSENGER_PLANE. In the call of SUPER->CONSTRUCTOR, remove the handling of classical exception WRONG_PLANETYPE. 5. Repeat the previous steps with local class LCL_CARGO_PLANE.

404

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

Task 4 Handle the raised exception in the main program whenever an airplane object is created. 1. Define a global reference variable for this purpose (suggested name: GO_INV_PLANETYPE) and type it with your exception class ZCX_##_INVALID_PLANETYPE. 2. In the CREATE OBJECT statement for airplanes (instances of LCL_AIRPLANE, LCL_PASSENGER_PLANE, and LCL_CARGO_PLANE), remove the handling of the classical, non class-based exception WRONG_PLANETYPE. 3. Surround each CREATE OBJECT statement for airplanes with a TRY-ENDTRY structure. Add a CATCH block for your exception ZCX_##_INVALID_PLANETYPE. In the case of an exception, let reference variable GO_INV_PLANETYPE point to the exception object. 4. Read the error text from the exception object and output it to the ABAP list. Hint: It is not possible to use the result of functional methods directly in the WRITE statement. You need to define a variable to store the text (suggested name: GV_TEXT with data type STRING). 5. Activate and test your program. For test purposes, create an airplane with a wrong plane type and debug the propagation of the exception.

© Copyright . All rights reserved.

405

Unit 9 Solution 23 Implement Class-Based Exceptions

Business Example  Your program should use the class-based exception concept if an invalid plane type is provided when creating an airplane instance. Template: SAPBC401_GCL_S2 Solution: SAPBC401_EXC_S1 (Main program) CX_INVALID_PLANETYPE (exception class) Task 1 Create a global exception class for an invalid airplane type. 1. Create a global exception class called ZCX_##_INVALID_PLANETYPE (where ## is your twodigit group number). Set the syntax check to ensure that exceptions based on this class are either handled directly or propagated. Choose the superclass accordingly. In the exception class, use texts from a message class instead of freely defined texts. Hint: To state whether or not the messages from a message class are used when you create the exception class,select the Message Class checkbox. a) Create a global class. b) On the following window, choose the CX_STATIC_CHECK superclass. c) Choose the Exception Class option and select the Message Class checkbox. 2. Add an attribute for the airplane type (suggested name: PLANETYPE) and assign the type S_PLANETYPE to it. Make sure a corresponding parameter is defined in the signature of the constructor.

406

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

Hint: You cannot define the constructor of an exception class directly. If you define the attribute as public, a corresponding import parameter is added to the constructor by the framework. a) Go to the Attributes tab. Enter the attribute name and type and choose the visibility. 3. Create a default error message. Include a placeholder in the message text so that it can be enhanced dynamically to include the airplane type. Hint: You can define your own message class and message or use message 020 from message class BC401. a) Go to the Texts tab. Select the default text and choose Message Text. b) Enter the message class and message number in the relevant fields. In the Attr. 1 field, use the value that helps to choose attribute PLANETYPE.

Task 2 Raise the new exception in method GET_TECHNICAL ATTRIBUTES of your local class LCL_AIRPLANE. 1. Complete program ZBC401_##_MAIN or copy the template program. a) Carry out this step as usual. Additional information is available in SAP Library. 2. Edit the definition of local class LCL_AIRPLANE. Remove the classical, non class-based exception WRONG_PLANETYPE from the signature of method GET_TECHNICAL_ATTRIBUTES and replace it with your new class-based exception ZCX_##_INVALID_PLANETYPE. a) See the source code extract from the model solution. 3. Edit the implementation of method GET_TECHNICAL_ATTRIBUTES and raise the class-based exception instead of the classical exception. Ensure that the wrong plane type value is handed over to the constructor and stored in the exception object. a) See the source code extract from the model solution. Task 3 Propagate the class-based exception explicitly through the entire call hierarchy so that you must handle it only once in the main program. 1. Edit the definition of local class LCL_AIRPLANE. Remove the classical, non class-based exception WRONG_PLANETYPE from the signature of method GET_TECHNICAL_ATTRIBUTES and replace it with your new class-based exception, ZCX_##_INVALID_PLANETYPE.

© Copyright . All rights reserved.

407

Unit 9: Object-Oriented Exception Handling

a) See the source code extract from the model solution. 2. Edit the implementation of the constructor of local class LCL_AIRPLANE. While calling method GET_TECHNICAL_ATTRIBUTES, remove the handling of classical exception WRONG_PLANETYPE. a) See the source code extract from the model solution. 3. Why is it not necessary to handle the class-based exception ZCX_##_INVALID_PLANETYPE here? It is because this exception is propagated in the signature of the constructor of LCL_AIRPLANE. 4. Edit the definition of local class LCL_PASSENGER_PLANE. Remove the classical, non classbased exception WRONG_PLANETYPE from the signature of the CONSTRUCTOR method and replace it with your new class-based exception ZCX_##_INVALID_PLANETYPE. Edit the implementation of the constructor of local class LCL_PASSENGER_PLANE. In the call of SUPER->CONSTRUCTOR, remove the handling of classical exception WRONG_PLANETYPE. a) See the source code extract from the model solution. 5. Repeat the previous steps with local class LCL_CARGO_PLANE. a) See the source code extract from the model solution. Task 4 Handle the raised exception in the main program whenever an airplane object is created. 1. Define a global reference variable for this purpose (suggested name: GO_INV_PLANETYPE) and type it with your exception class ZCX_##_INVALID_PLANETYPE. a) See the source code extract from the model solution. 2. In the CREATE OBJECT statement for airplanes (instances of LCL_AIRPLANE, LCL_PASSENGER_PLANE, and LCL_CARGO_PLANE), remove the handling of the classical, non class-based exception WRONG_PLANETYPE. a) See the source code extract from the model solution. 3. Surround each CREATE OBJECT statement for airplanes with a TRY-ENDTRY structure. Add a CATCH block for your exception ZCX_##_INVALID_PLANETYPE. In the case of an exception, let reference variable GO_INV_PLANETYPE point to the exception object. a) See the source code extract from the model solution. 4. Read the error text from the exception object and output it to the ABAP list. Hint: It is not possible to use the result of functional methods directly in the WRITE statement. You need to define a variable to store the text (suggested name: GV_TEXT with data type STRING).

408

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

a) See the source code extract from the model solution. 5. Activate and test your program. For test purposes, create an airplane with a wrong plane type and debug the propagation of the exception. a) Perform this step in the usual manner. Include BC401_EXC_S1_CARRIER *------------------------------------------------* * CLASS lcl_airplane DEFINITION *------------------------------------------------* CLASS lcl_airplane DEFINITION. PUBLIC SECTION.

* *

METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype EXCEPTIONS wrong_planetype, RAISING cx_invalid_planetype, display_attributes. CLASS-METHODS: display_n_o_airplanes, class_constructor. EVENTS: airplane_created. PROTECTED SECTION. CONSTANTS: c_pos_1 TYPE i VALUE 30. PRIVATE SECTION. TYPES: ty_planetypes TYPE STANDARD TABLE OF saplane WITH NON-UNIQUE KEY planetype. DATA: mv_name mv_planetype mv_weight mv_tankcap

TYPE TYPE TYPE TYPE

string, saplane-planetype, saplane-weight, saplane-tankcap.

CLASS-DATA: gv_n_o_airplanes TYPE i, gt_planetypes TYPE ty_planetypes. CLASS-METHODS: get_technical_attributes

© Copyright . All rights reserved.

409

Unit 9: Object-Oriented Exception Handling

* *

IMPORTING iv_type TYPE saplane-planetype EXPORTING ev_weight TYPE saplane-weight ev_tankcap TYPE saplane-tankcap EXCEPTIONS wrong_planetype. RAISING cx_invalid_planetype.

ENDCLASS.

"lcl_airplane DEFINITION

*-------------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION *-------------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. METHOD class_constructor. SELECT * FROM saplane INTO TABLE gt_planetypes. ENDMETHOD. "class_constructor METHOD constructor. mv_name = iv_name. mv_planetype = iv_planetype. get_technical_attributes( EXPORTING iv_type = iv_planetype IMPORTING ev_weight = mv_weight ev_tankcap = mv_tankcap ). gv_n_o_airplanes = gv_n_o_airplanes + 1. RAISE EVENT airplane_created. * * * * * * * * * * * * * * *

get_technical_attributes( EXPORTING iv_type = iv_planetype IMPORTING ev_weight = mv_weight ev_tankcap = mv_tankcap EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ELSE. gv_n_o_airplanes = gv_n_o_airplanes + 1. RAISE EVENT airplane_created. ENDIF. ENDMETHOD. "constructor METHOD display_attributes. WRITE: / icon_ws_plane AS ICON, / 'Name of Airplane'(001) , AT c_pos_1 mv_name, / 'Type of Airplane:'(002), AT c_pos_1 mv_planetype, / 'Weight:'(003), AT c_pos_1 mv_weight LEFT-JUSTIFIED,

410

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

/ 'Tank capacity:'(004), LEFT-JUSTIFIED. ENDMETHOD.

AT c_pos_1 mv_tankcap

"display_attributes

METHOD display_n_o_airplanes. SKIP. WRITE: / 'Number of airplanes:'(ca1), AT c_pos_1 gv_n_o_airplanes LEFT-JUSTIFIED. ENDMETHOD. "display_n_o_airplanes METHOD get_technical_attributes. DATA: ls_planetype TYPE saplane. READ TABLE gt_planetypes INTO ls_planetype WITH TABLE KEY planetype = iv_type TRANSPORTING weight tankcap. IF sy-subrc = 0. ev_weight = ls_planetype-weight. ev_tankcap = ls_planetype-tankcap. ELSE. * RAISE wrong_planetype. RAISE EXCEPTION TYPE cx_invalid_planetype EXPORTING planetype = iv_type. ENDIF. ENDMETHOD. "get_technical_attributes ENDCLASS.

"lcl_airplane IMPLEMENTATION

*-------------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *---------------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. PUBLIC SECTION.

* *

METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype iv_cargo TYPE s_plan_car RAISING cx_invalid_planetype, EXCEPTIONS wrong_planetype, display_attributes REDEFINITION. PRIVATE SECTION. DATA: mv_cargo TYPE s_plan_car.

© Copyright . All rights reserved.

411

Unit 9: Object-Oriented Exception Handling

ENDCLASS.

"lcl_cargo_plane DEFINITION

*-----------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *-----------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION.

* * * * *

METHOD constructor. super->constructor( EXPORTING iv_name = iv_name iv_planetype = iv_planetype ). EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ENDIF. mv_cargo = iv_cargo. ENDMETHOD. "constructor METHOD display_attributes. super->display_attributes( ). WRITE: / 'Max Cargo:'(005), AT c_pos_1 mv_cargo LEFT-JUSTIFIED. ULINE. ENDMETHOD. "display_attributes

ENDCLASS.

"lcl_cargo_plane IMPLEMENTATION

*------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane. PUBLIC SECTION.

* *

METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype iv_seats TYPE s_seatsmax EXCEPTIONS wrong_planetype RAISING cx_invalid_planetype, display_attributes REDEFINITION. PRIVATE SECTION. DATA: mv_seats TYPE s_seatsmax.

ENDCLASS.

412

"lcl_passenger_plane DEFINITION

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

*-----------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *-----------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. METHOD constructor. super->constructor( EXPORTING iv_name = iv_name iv_planetype = iv_planetype ). * * * * *

EXCEPTIONS wrong_planetype = 1 ). IF sy-subrc 0. RAISE wrong_planetype. ENDIF. mv_seats = iv_seats. ENDMETHOD. "constructor

METHOD display_attributes. super->display_attributes( ). WRITE: / 'Max Seats:'(006), AT c_pos_1 mv_seats LEFT-JUSTIFIED. ULINE. ENDMETHOD. "display_attributes ENDCLASS. "lcl_passenger_plane IMPLEMENTATION *---------------------------------------------------* * CLASS lcl_carrier DEFINITION *---------------------------------------------------* CLASS lcl_carrier DEFINITION. ... ENDCLASS.

"lcl_carrier DEFINITION

*---------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *---------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. ... ENDCLASS.

"lcl_carrier IMPLEMENTATION Main program SAPBC401_EXC_S1

REPORT

sapbc401_exc_s1.

TYPE-POOLS icon. INCLUDE bc401_exc_s1_agency. INCLUDE bc401_exc_s1_carrier. INCLUDE bc401_exc_s1_rental.

© Copyright . All rights reserved.

413

Unit 9: Object-Oriented Exception Handling

DATA: go_hotel go_vehicle go_truck go_bus go_rental go_passenger go_cargo go_carrier go_agency

TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE

REF REF REF REF REF REF REF REF REF

TO TO TO TO TO TO TO TO TO

cl_hotel2, lcl_vehicle, lcl_truck, lcl_bus, lcl_rental, lcl_passenger_plane, lcl_cargo_plane, lcl_carrier, lcl_travel_agency.

DATA: gv_text TYPE string, gx_inv_planetype TYPE REF TO cx_invalid_planetype. START-OF-SELECTION. ******************* ******* create travel_agency CREATE OBJECT go_agency EXPORTING iv_name = 'Travel&Smile Travel'. ******* create hotel CREATE OBJECT go_hotel EXPORTING iv_name = 'Sleep Well Hotel' iv_beds = 345. ******* create rental CREATE OBJECT go_rental EXPORTING iv_name = 'Happy Car Rental'. ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'MAN' iv_cargo = 45. ******* create truck CREATE OBJECT go_bus EXPORTING iv_make = 'Mercedes' iv_passengers = 80. ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'VOLVO' iv_cargo = 48. ***** Create Carrier CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly'.

414

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

***** Passenger Plane TRY. CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-500' iv_seats = 345. CATCH cx_invalid_planetype INTO gx_inv_planetype. gv_text = gx_inv_planetype->get_text( ). WRITE: / icon_failure AS ICON, gv_text. ENDTRY. * * * * * * * * * * * *

CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-400' iv_seats = 345 EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. WRITE: / icon_failure AS ICON, 'Wrong plane type'. ENDIF.

***** cargo Plane TRY. CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533. CATCH cx_invalid_planetype INTO gx_inv_planetype. gv_text = gx_inv_planetype->get_text( ). WRITE: / icon_failure AS ICON, gv_text. ENDTRY. * * * * * * * * * * * *

CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533 EXCEPTIONS wrong_planetype = 1. IF sy-subrc 0. WRITE: / icon_failure AS ICON, 'Wrong plane type'.

© Copyright . All rights reserved.

415

Unit 9: Object-Oriented Exception Handling

*

ENDIF.

******* show attributes of all partners of travel_agency go_agency->display_attributes( ).

416

© Copyright . All rights reserved.

Lesson: Defining and Raising Exceptions

LESSON SUMMARY You should now be able to: ●

Define global exception classes



Raise class-based exceptions



Propagate exceptions

© Copyright . All rights reserved.

417

Unit 9 Lesson 3 Implementing Advanced Exception Handling Techniques

LESSON OVERVIEW This lesson explains the implementation of advanced exception handling techniques. Business Example You need to use advanced exception handling techniques to catch exceptions and to retry after exception handling in your ABAP Objects programs. For this reason, you require the following knowledge: ●

An understanding of predefined exception classes



An understanding of how to handle an exception class



An understanding of how to retry after an exception

LESSON OBJECTIVES After completing this lesson, you will be able to:

418



Explain the hierarchy of predefined exception classes



Explain different ways of handling an exception



Retry after exceptions



Implement resumable exceptions



Reraise exceptions



Map exceptions to each other

© Copyright . All rights reserved.

Lesson: Implementing Advanced Exception Handling Techniques

The Hierarchy of Predefined Exception Classes

Figure 155: Integration of Standard Exceptions in the Runtime System

The figure illustrates the consequences that may arise as you choose the superclass of an exception class. It also shows how the standard exceptions in the runtime system are integrated into the inheritance hierarchy of the exception classes. The choice of the superclass influences the way that the syntax check and the runtime environment handle a given exception. Some of the standard exception classes are as follows: CX_STATIC_CHECK



If an exception class inherits from CX_STATIC_CHECK, you must either handle the relevant exception or propagate it using the RAISING addition. If the exception class is not handled using the Raising addition, the syntax check displays a warning. When you define a new global exception class, CX_STATIC_CHECK is defined as the superclass by default. ●

CX_DYNAMIC_CHECK For subclasses of CX_DYNAMIC_CHECK, the syntax check displays no warning if exceptions are neither handled nor propagated with the RAISING addition.If an exception is raised at runtime and you neither handle nor propagate it, the system ends the program with a runtime error.

© Copyright . All rights reserved.

419

Unit 9: Object-Oriented Exception Handling

Note: Typical examples of this situation are the predefined exceptions CX_SY_... for errors that occur in the runtime environment. These are usually subclasses of CX_DYNAMIC_CHECK. CX_NO_CHECK



For subclasses of CX_NO_CHECK, you cannot propagate the corresponding exceptions explicitly using the RAISING addition. If you do not handlethese exceptions in the processing block where they occur, they are automatically propagated. If the calling block does not handle the exceptions,they are automatically propagated further on to the highest call hierarchy level. If the exceptions are not handled on the top level, a runtime error occurs at the point where they were raised. Some predefined exceptions with the prefix CX_SY_... for error situations in the runtime environment are subclasses of CX_NO_CHECK.

Different Ways of Handling an Exception After an exception was caught in a CATCH statement, you can handle it without stopping the program. Use the following techniques to handle an exception caught in a CATCH statement without stopping the program: 1. Continue the program behind an ENDTRY statement after taking one of the following actions: ●

Ignoring the exception (do nothing)



Issuing a warning



Writing to a protocol



Correcting the situation

2. Remove the cause of the error and start again from one of the following points: ●



From the beginning of the corresponding TRY block using statement RETRY that is new as of SAP NW 7.0 EhP 2. From where the exception occurred (using statement RESUME that is new as of SAP NW 7.0 EhP 2).

3. Raise and propagate one of the following exceptions:

420



The same exception object again using RAISE EXCEPTION .



A new exception using RAISE EXCEPTION TYPE .

© Copyright . All rights reserved.

Lesson: Implementing Advanced Exception Handling Techniques

Implementation of Retry After Exceptions

Figure 156: RETRY statement

When you handle an exception in a CATCH block, use the RETRYstatement to go back to the TRY statement of the respective TRY-ENDTRY structure, for example, if the cause for the exception was removed during the handling. Hint: This technique is new with Release SAP NetWeaver 7.0 EhP 2.

In the example, the main program catches the exception that the constructor raised and propagated. After analyzing the exception object and correcting the error situation, the main program repeats the whole TRY block using the RETRY statement.

Caution: You must use RETRY with some caution. If you do not remove the cause of the exception properly, your program will go into an infinite loop.

© Copyright . All rights reserved.

421

Unit 9: Object-Oriented Exception Handling

Implementation of Resumable Exceptions

Figure 157: RETRY statement

Hint: This technique is new with Release SAP NW 7.0 EhP 2.

Use the RESUME statement to resume a program immediately after the statement that raised the exception in the source code. You must satisfy the following prerequisites to use the RESUME statement: 1. The exception must be caught with CATCH statement using the addition BEFORE UNWIND. This ensures that the context of the exception is kept alive for a possible RESUME. If the CATCH block exited without the RESUME statement, the system deletes the context in which the exception was raised after the CATCH block is exited. 2. The exception must be raised with the RAISE RESUMABLE ... variant of the RAISE EXCEPTION statement. This prepares the raising processing lock for the RESUME. 3. If the exception is propagated, you must mark it as resumable on all hierarchy levels by using the RAISING RESUMABLE ( ... ) addition with the name of the exception class inside the brackets. This prepares all methods that propagate the exception for a possible RESUME.

422

© Copyright . All rights reserved.

Lesson: Implementing Advanced Exception Handling Techniques

Hint: Respective checkboxes are available in Class Builder and Function Builder when defining the signature of a method or the interface of a function module. The handler of a given exception checks whether, at runtime a given exception was raised and propagated resumable or not. All exception objects provide public instance attribute IS_RESUMABLE, which is set to ’X’ or ’ ’ by the framework, depending on how the exception was raised and propagated. If you resume a non-resumable exception, you cause a runtime error (exception class CX_SY_ILLEGAL_HANDLER). Resume Execution After a Resumable Exception

Figure 158: Resume Execution After a Resumable Exception

In the example, shown in the figure, method GET_TECH_ATTR raises and propagates the exception; the constructor propagates the exception further. All raising and propagating is setup to be resumable. The main program handles the exception with CATCH BEFORE UNWIND ..., checks that the exception indeed is resumable, and issues the RESUME statement. The system resumes the execution of GET_TECH_ATTR immediately after the RAISE RESUMABLE EXCEPTION statement is executed.

Hint: In this example, you keep the context of the exception. If you do not add the BEFORE UNWIND addition, the system deletes the newly created instance before executing the CATCH block. You will not be able to resume the GET_TECH_ATTR method and the constructor would not be executed.

© Copyright . All rights reserved.

423

Unit 9: Object-Oriented Exception Handling

Implementation of Re-Raise Exceptions

Figure 159: Reraising an Existing Exception Object

You re-raise class-based exceptions with one of the following variants of statement RAISE EXCEPTION: ●

RAISE EXCEPTION TYPE [EXPORTING ...] This statement creates a new exception object, which is an instance of class . Optionally, values can be provided for the constructor using the EXPORTING addition.



RAISE EXCEPTION This statement uses an existing exception object, namely whichever exception object points to. This exception object iseither created directly, using a CREATE OBJECT statement or, more commonly, caught in a previous CATCH ... INTO ... statement and  pass explicitly to the caller.

In the example, the constructor catches exception CX_EXC, which is raised by the GET_TECH_ATTR method. The constructor analyzes the exception object, performs necessary adjustments, issues a warning, and so on. The constructor then decides to pass the exception to the main program, where the exception is handled again.

424

© Copyright . All rights reserved.

Lesson: Implementing Advanced Exception Handling Techniques

Mapping of Exceptions to Each Other

Figure 160: Mapping Exceptions to Each Other

After catching an exception, the program can raise a second exception,and so on. An exception object becomes invalid once it leaves the CATCH block. Therefore, the handler on the top level can only access the last exceptionobject. However,you can chain exception objects, that is, you can let one exceptionobject point to the one before, which points to the one before it, and so on. The handler of an exception follows the chain and evaluates each exception object in the sequence. All exception classes provide a public instance attribute PREVIOUS.You type the attributewith REF TO CX_ROOTto point to arbitrary exception objects.The constructors of all exception classes have an import parameter, PREVIOUS, of the same type, which can be used to link an existing exception object to a new one. In the example in the figure, the constructor catches the exception that has been raised by the GET_TECH_ATTR method. After analyzing the exception, the constructor raises a new exception of a different exception class. It chains the existing exception object to the new one by passing a reference to the existing object to the constructor of the new object. As a result, attribute PREVIOUS of the new exception object points to the exception object that preceded it. The main program catches the second exception and accesses to the second exception object. However, by using public attribute PREVIOUS, the main program can navigate to the other exception object and analyze it. The main program can access each instance in a chain of exceptions and follow the history of the raised exceptions in the call hierarchy.

© Copyright . All rights reserved.

425

Unit 9: Object-Oriented Exception Handling

426

© Copyright . All rights reserved.

Unit 9 Exercise 24 Map Exceptions to Each Other

Business Example You want your program to use the class-based exception concept if an invalid plane type is provided when creating an airplane instance. Instead of just propagating the exception raised by GET_TECHNICAL_ATTRIBUTES, the constructor needs to handle it and raise a different exception. You want the two exceptions to be chained together so that the main program can evaluate both. Template: SAPBC401_EXC_S1 Solution: SAPBC401_EXC_S2 Task 1 In the constructor of local class LCL_AIRPLANE, handle the exception raised by method GET_TECHNICAL_ATTRIBUTES. 1. Complete program ZBC401_##_MAIN or copy the template program. 2. Edit the implementation of the constructor of local class LCL_AIRPLANE. Define a local object reference (suggested name: LX_INV_PLANETYPE) and enter it so that it points to the exception object raised by method GET_TECHNICAL_ATTRIBUTES. 3. Implement a TRY-ENDTRY structure for exception handling. Catch the exception object, but leave the CATCH block empty for now.

Task 2 Raise a new exception and map it to the original one. Adjust the constructor to propagate the new exception to the main program. 1. In the constructor of LCL_AIRPLANE, map the new exception with the original one raised by get_technical_attributes so that the constructor handles both exceptions. Hint: Check the signature of exception class CX_INVALID_VALUE to see if you need to provide values for any attributes it contains. Transfer the reference to the original exception instance to the exception instance constructor.

© Copyright . All rights reserved.

427

Unit 9: Object-Oriented Exception Handling

2. Adjust the signature of the constructor so that it propagates the new exception. 3. Which other method signatures do you have to adjust to propagate the exception up to the main program?

Task 3 In the main program, handle the new exception and evaluate the information of both, the new and the original exception instance. 1. Catch your new exception in the main program everytime you create an instance of an airplane. Define a local reference variable for the purpose with a suitable reference type (suggested name: GX_INV_VALUE). 2. Use this reference to extract the text of your new exception. Output the text on the list. 3. Use the same variables to export the text of the original exception. Output the text on the list.

428

© Copyright . All rights reserved.

Unit 9 Solution 24 Map Exceptions to Each Other

Business Example You want your program to use the class-based exception concept if an invalid plane type is provided when creating an airplane instance. Instead of just propagating the exception raised by GET_TECHNICAL_ATTRIBUTES, the constructor needs to handle it and raise a different exception. You want the two exceptions to be chained together so that the main program can evaluate both. Template: SAPBC401_EXC_S1 Solution: SAPBC401_EXC_S2 Task 1 In the constructor of local class LCL_AIRPLANE, handle the exception raised by method GET_TECHNICAL_ATTRIBUTES. 1. Complete program ZBC401_##_MAIN or copy the template program. a) Carry out this step as usual. For more information, refer to the SAP Library. 2. Edit the implementation of the constructor of local class LCL_AIRPLANE. Define a local object reference (suggested name: LX_INV_PLANETYPE) and enter it so that it points to the exception object raised by method GET_TECHNICAL_ATTRIBUTES. a) Refer the source code extract from the model solution. 3. Implement a TRY-ENDTRY structure for exception handling. Catch the exception object, but leave the CATCH block empty for now. a) Refer the source code extract from the model solution.

Task 2 Raise a new exception and map it to the original one. Adjust the constructor to propagate the new exception to the main program. 1. In the constructor of LCL_AIRPLANE, map the new exception with the original one raised by get_technical_attributes so that the constructor handles both exceptions.

© Copyright . All rights reserved.

429

Unit 9: Object-Oriented Exception Handling

Hint: Check the signature of exception class CX_INVALID_VALUE to see if you need to provide values for any attributes it contains. Transfer the reference to the original exception instance to the exception instance constructor. a) Refer the source code extract from the model solution. 2. Adjust the signature of the constructor so that it propagates the new exception. a) Refer the source code extract from the model solution. 3. Which other method signatures do you have to adjust to propagate the exception up to the main program? The constructors of LCL_CARGO_PLANE and LCL_PASSENGER_PLANE. Task 3 In the main program, handle the new exception and evaluate the information of both, the new and the original exception instance. 1. Catch your new exception in the main program everytime you create an instance of an airplane. Define a local reference variable for the purpose with a suitable reference type (suggested name: GX_INV_VALUE). a) Refer the source code extract from the model solution. 2. Use this reference to extract the text of your new exception. Output the text on the list. a) Refer the source code extract from the model solution. 3. Use the same variables to export the text of the original exception. Output the text on the list. a) Refer the source code extract from the model solution. Include BC401_EXC_S2_CARRIER *---------------------------------------------------* * CLASS lcl_airplane DEFINITION *---------------------------------------------------* CLASS lcl_airplane DEFINITION. PUBLIC SECTION.

*

430

METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype RAISING cx_invalid_value, cx_invalid_planetype,

© Copyright . All rights reserved.

Lesson: Implementing Advanced Exception Handling Techniques

display_attributes. CLASS-METHODS: display_n_o_airplanes, class_constructor. EVENTS: airplane_created. PROTECTED SECTION. CONSTANTS: c_pos_1 TYPE i VALUE 30. PRIVATE SECTION. TYPES: ty_planetypes TYPE STANDARD TABLE OF saplane WITH NON-UNIQUE KEY planetype. DATA: mv_name mv_planetype mv_weight mv_tankcap

TYPE TYPE TYPE TYPE

string, saplane-planetype, saplane-weight, saplane-tankcap.

CLASS-DATA: gv_n_o_airplanes TYPE i, gt_planetypes TYPE ty_planetypes. CLASS-METHODS: get_technical_attributes IMPORTING iv_type TYPE saplane-planetype EXPORTING ev_weight TYPE saplane-weight ev_tankcap TYPE saplane-tankcap RAISING cx_invalid_planetype. ENDCLASS.

"lcl_airplane DEFINITION

*-----------------------------------------------* * CLASS lcl_airplane IMPLEMENTATION * *-----------------------------------------------* CLASS lcl_airplane IMPLEMENTATION. METHOD class_constructor. SELECT * FROM saplane INTO TABLE gt_planetypes. ENDMETHOD. "class_constructor METHOD constructor. DATA: lx_inv_planetype TYPE REF TO cx_invalid_planetype. mv_name = iv_name. mv_planetype = iv_planetype.

© Copyright . All rights reserved.

431

Unit 9: Object-Oriented Exception Handling

TRY.

get_technical_attributes( EXPORTING iv_type = iv_planetype IMPORTING ev_weight = mv_weight ev_tankcap = mv_tankcap ). gv_n_o_airplanes = gv_n_o_airplanes + 1. RAISE EVENT airplane_created.

CATCH cx_invalid_planetype INTO lx_inv_planetype. RAISE EXCEPTION TYPE cx_invalid_value EXPORTING parnam = 'IV_PLANETYPE' previous = lx_inv_planetype. ENDTRY. ENDMETHOD.

"constructor

METHOD display_attributes. WRITE: / icon_ws_plane AS ICON, / 'Name of Airplane'(001) , / 'Type of Airplane:'(002), / 'Weight:'(003), LEFT-JUSTIFIED, / 'Tank capacity:'(004), LEFT-JUSTIFIED. ENDMETHOD.

AT c_pos_1 mv_name, AT c_pos_1 mv_planetype, AT c_pos_1 mv_weight AT c_pos_1 mv_tankcap

"display_attributes

METHOD display_n_o_airplanes. SKIP. WRITE: / 'Number of airplanes:'(ca1), AT c_pos_1 gv_n_o_airplanes LEFT-JUSTIFIED. ENDMETHOD. "display_n_o_airplanes METHOD get_technical_attributes. DATA: ls_planetype TYPE saplane. READ TABLE gt_planetypes INTO ls_planetype WITH TABLE KEY planetype = iv_type TRANSPORTING weight tankcap. IF sy-subrc = 0. ev_weight = ls_planetype-weight. ev_tankcap = ls_planetype-tankcap. ELSE. * RAISE wrong_planetype. RAISE EXCEPTION TYPE cx_invalid_planetype EXPORTING planetype = iv_type. ENDIF. ENDMETHOD. "get_technical_attributes

432

© Copyright . All rights reserved.

Lesson: Implementing Advanced Exception Handling Techniques

ENDCLASS.

"lcl_airplane IMPLEMENTATION

*------------------------------------------------* * CLASS lcl_cargo_plane DEFINITION *------------------------------------------------* * *----------------------------------------------------* CLASS lcl_cargo_plane DEFINITION INHERITING FROM lcl_airplane. PUBLIC SECTION.

*

METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype iv_cargo TYPE s_plan_car RAISING cx_invalid_value, cx_invalid_planetype, display_attributes REDEFINITION. PRIVATE SECTION. DATA: mv_cargo TYPE s_plan_car.

ENDCLASS.

"lcl_cargo_plane DEFINITION

*-------------------------------------------------* * CLASS lcl_cargo_plane IMPLEMENTATION *-------------------------------------------------* CLASS lcl_cargo_plane IMPLEMENTATION. ... ENDCLASS.

"lcl_cargo_plane IMPLEMENTATION

*-------------------------------------------------* * CLASS lcl_passenger_plane DEFINITION *-------------------------------------------------* CLASS lcl_passenger_plane DEFINITION INHERITING FROM lcl_airplane. PUBLIC SECTION.

*

METHODS: constructor IMPORTING iv_name TYPE string iv_planetype TYPE saplane-planetype iv_seats TYPE s_seatsmax RAISING cx_invalid_value, cx_invalid_planetype, display_attributes REDEFINITION.

© Copyright . All rights reserved.

433

Unit 9: Object-Oriented Exception Handling

PRIVATE SECTION. DATA: mv_seats TYPE s_seatsmax. ENDCLASS. "lcl_passenger_plane DEFINITION *------------------------------------------------* * CLASS lcl_passenger_plane IMPLEMENTATION *------------------------------------------------* CLASS lcl_passenger_plane IMPLEMENTATION. ... ENDCLASS.

"lcl_passenger_plane IMPLEMENTATION

*------------------------------------------------* * CLASS lcl_carrier DEFINITION *------------------------------------------------* CLASS lcl_carrier DEFINITION. ... ENDCLASS. "lcl_carrier DEFINITION *------------------------------------------------* * CLASS lcl_carrier IMPLEMENTATION *------------------------------------------------* CLASS lcl_carrier IMPLEMENTATION. ... ENDCLASS.

"lcl_carrier IMPLEMENTATION Main Program SAPBC401_EXC_S2

REPORT

sapbc401_exc_s2.

TYPE-POOLS icon. INCLUDE bc401_exc_s2_agency. INCLUDE bc401_exc_s2_carrier. INCLUDE bc401_exc_s2_rental. DATA: go_hotel go_vehicle go_truck go_bus go_rental go_passenger go_cargo go_carrier go_agency

TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE TYPE

REF REF REF REF REF REF REF REF REF

TO TO TO TO TO TO TO TO TO

cl_hotel2, lcl_vehicle, lcl_truck, lcl_bus, lcl_rental, lcl_passenger_plane, lcl_cargo_plane, lcl_carrier, lcl_travel_agency.

DATA: gv_text TYPE string, gx_inv_value TYPE REF TO cx_invalid_value. * gx_inv_planetype TYPE REF TO cx_invalid_planetype.

434

© Copyright . All rights reserved.

Lesson: Implementing Advanced Exception Handling Techniques

START-OF-SELECTION. ******************* ******* create travel_agency CREATE OBJECT go_agency EXPORTING iv_name = 'Travel&Smile Travel'. ******* create hotel CREATE OBJECT go_hotel EXPORTING iv_name = 'Sleep Well Hotel' iv_beds = 345. ******* create rental CREATE OBJECT go_rental EXPORTING iv_name = 'Happy Car Rental'. ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'MAN' iv_cargo = 45. ******* create truck CREATE OBJECT go_bus EXPORTING iv_make = 'Mercedes' iv_passengers = 80. ******* create truck CREATE OBJECT go_truck EXPORTING iv_make = 'VOLVO' iv_cargo = 48. ***** Create Carrier CREATE OBJECT go_carrier EXPORTING iv_name = 'Smile&Fly'. ***** Passenger Plane TRY. CREATE OBJECT go_passenger EXPORTING iv_name = 'LH BERLIN' iv_planetype = '747-500' iv_seats = 345. CATCH cx_invalid_value INTO gx_inv_value. gv_text = gx_inv_value->get_text( ). WRITE: / icon_failure AS ICON, gv_text. gv_text = gx_inv_value->previous->get_text( ).

© Copyright . All rights reserved.

435

Unit 9: Object-Oriented Exception Handling

WRITE: / icon_failure AS ICON, gv_text. * * * * *

CATCH cx_invalid_planetype INTO gx_inv_planetype. gv_text = gx_inv_planetype->get_text( ). WRITE: / icon_failure AS ICON, gv_text. ENDTRY.

***** cargo Plane TRY. CREATE OBJECT go_cargo EXPORTING iv_name = 'US Hercules' iv_planetype = '747-200F' iv_cargo = 533. CATCH cx_invalid_value INTO gx_inv_value. gv_text = gx_inv_value->get_text( ). WRITE: / icon_failure AS ICON, gv_text. gv_text = gx_inv_value->previous->get_text( ). WRITE: / icon_failure AS ICON, gv_text. * * * * *

CATCH cx_invalid_planetype INTO gx_inv_planetype. gv_text = gx_inv_planetype->get_text( ). WRITE: / icon_failure AS ICON, gv_text. ENDTRY.

***** show attributes of all partners of travel_agency go_agency->display_attributes( ).

436

© Copyright . All rights reserved.

Lesson: Implementing Advanced Exception Handling Techniques

LESSON SUMMARY You should now be able to: ●

Explain the hierarchy of predefined exception classes



Explain different ways of handling an exception



Retry after exceptions



Implement resumable exceptions



Reraise exceptions



Map exceptions to each other

© Copyright . All rights reserved.

437

Unit 9: Object-Oriented Exception Handling

438

© Copyright . All rights reserved.

Unit 9 Learning Assessment

1. Which of the following statement is used to raise class-based exceptions?  Choose the correct answer. X

A EXPORTING

X

B RAISE EXCEPTION

X

C CREATE OBJECT

X

D CATCH

2. Which of the following block is used to catch and handle exceptions?  Choose the correct answer. X

A IMPORTING….RETURNING

X

B METHOD…. ENDMETHOD

X

C TRY … ENDTRY

X

D TRY...CATCH...ENDTRY

3. An exception can only be handled if the statement that raised it is enclosed in a TRY-ENDTRY control structure.  Determine whether this statement is true or false. X

True

X

False

4. TRY-ENDTRY structures can be nested to any depth.  Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

439

Unit 9: Learning Assessment

5. You can specify only two exception classes to the CATCH statement. Determine whether this statement is true or false. X

True

X

False

6. If an exception is raised, the name of the exception class is displayed in the __________ field in debugging mode. Choose the correct answer. X

A exception raised

X

B last exception object

X

C watchpoint

X

D layout

7. Which of the following options can be selected when you create an exception class? Choose the correct answer. X

A The exception class radio button

X

B The with Message Class checkbox

X

C The usual ABAP Class radio button

8. Which of the following is the step to define global exception classes? Choose the correct answer.

440

X

A Create a global class with the class type as exception class.

X

B Define additional attributes.

X

C Save as exception texts.

X

D Activate the exception class.

© Copyright . All rights reserved.

Unit 9: Learning Assessment

9. Which of the following syntax addition is used to propagate an exception from a procedure? Choose the correct answer. X

A CATCH

X

B RAISING

X

C METHODS

X

D FORM

10. Which of the following blocks of code is executed before the CATCH block of the main program after an exception has occurred? Choose the correct answers. X

A CLEANUP

X

B TRY

X

C CATCH

X

D RESUME

11. For subclasses of ____________ the corresponding exceptions cannot be propagated explicitly using the RAISING addition. Choose the correct answer. X

A CX_STATIC_CHECK

X

B CX_NO_CHECK

X

C CX_DYNAMIC_CHECK

12. Which of the following is/are the way(s) to handle exception besides stopping the program? Choose the correct answers. X

A Continue program

X

B Remove the cause of error

X

C Do not propagate an exception

X

D Call method CX_SYSTEM_HANDLE

© Copyright . All rights reserved.

441

Unit 9: Learning Assessment

13. Which of the following is used to jump back to the TRY statement? Choose the correct answer. X

A RETRY

X

B CATCH

X

C TRY-ENTRY

X

D RAISE

14. Which of the following is a prerequisite for using the RESUME statement? Choose the correct answers. X

A The exception has to be caught.

X

B The exception has to marked resumable.

X

C The exception has to be propagated.

X

D The exception has to be raised.

15. Which of the following statements raise a new exception object? Choose the correct answers.

442

X

A RAISE

X

B RESUME

X

C CATCH

© Copyright . All rights reserved.

Unit 9 Learning Assessment - Answers

1. Which of the following statement is used to raise class-based exceptions?  Choose the correct answer. X

A EXPORTING

X

B RAISE EXCEPTION

X

C CREATE OBJECT

X

D CATCH

2. Which of the following block is used to catch and handle exceptions?  Choose the correct answer. X

A IMPORTING….RETURNING

X

B METHOD…. ENDMETHOD

X

C TRY … ENDTRY

X

D TRY...CATCH...ENDTRY

3. An exception can only be handled if the statement that raised it is enclosed in a TRY-ENDTRY control structure.  Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

443

Unit 9: Learning Assessment - Answers

4. TRY-ENDTRY structures can be nested to any depth.  Determine whether this statement is true or false. X

True

X

False

5. You can specify only two exception classes to the CATCH statement. Determine whether this statement is true or false. X

True

X

False

6. If an exception is raised, the name of the exception class is displayed in the __________ field in debugging mode. Choose the correct answer. X

A exception raised

X

B last exception object

X

C watchpoint

X

D layout

7. Which of the following options can be selected when you create an exception class? Choose the correct answer.

444

X

A The exception class radio button

X

B The with Message Class checkbox

X

C The usual ABAP Class radio button

© Copyright . All rights reserved.

Unit 9: Learning Assessment - Answers

8. Which of the following is the step to define global exception classes? Choose the correct answer. X

A Create a global class with the class type as exception class.

X

B Define additional attributes.

X

C Save as exception texts.

X

D Activate the exception class.

9. Which of the following syntax addition is used to propagate an exception from a procedure? Choose the correct answer. X

A CATCH

X

B RAISING

X

C METHODS

X

D FORM

10. Which of the following blocks of code is executed before the CATCH block of the main program after an exception has occurred? Choose the correct answers. X

A CLEANUP

X

B TRY

X

C CATCH

X

D RESUME

11. For subclasses of ____________ the corresponding exceptions cannot be propagated explicitly using the RAISING addition. Choose the correct answer. X

A CX_STATIC_CHECK

X

B CX_NO_CHECK

X

C CX_DYNAMIC_CHECK

© Copyright . All rights reserved.

445

Unit 9: Learning Assessment - Answers

12. Which of the following is/are the way(s) to handle exception besides stopping the program? Choose the correct answers. X

A Continue program

X

B Remove the cause of error

X

C Do not propagate an exception

X

D Call method CX_SYSTEM_HANDLE

13. Which of the following is used to jump back to the TRY statement? Choose the correct answer. X

A RETRY

X

B CATCH

X

C TRY-ENTRY

X

D RAISE

14. Which of the following is a prerequisite for using the RESUME statement? Choose the correct answers. X

A The exception has to be caught.

X

B The exception has to marked resumable.

X

C The exception has to be propagated.

X

D The exception has to be raised.

15. Which of the following statements raise a new exception object? Choose the correct answers.

446

X

A RAISE

X

B RESUME

X

C CATCH

© Copyright . All rights reserved.

UNIT 10

Program Calls and Memory Management

Lesson 1 Using Shared Objects Exercise 25: Use Shared Objects

448 467

UNIT OBJECTIVES ●

Explain shared objects



Use shared objects

© Copyright . All rights reserved.

447

Unit 10 Lesson 1 Using Shared Objects

LESSON OVERVIEW This lesson explains how you can save data as shared objects in shared memory, and examine this concept and its implementation.  ​ Business Example You want to develop a transaction in which many users can access the same data concurrently without having to read it from the database each time. You know that shared objects can be used to make data in the main memory accessible across session boundaries. Accordingly, you must familiarize yourself with this technique. For this reason, you require the following knowledge: ●

An understanding of how classes are created for shared objects



An understanding of how you can use shared objects to implement applications



An understanding of access shared objects from within an ABAP program

LESSON OBJECTIVES After completing this lesson, you will be able to: ●

Explain shared objects



Use shared objects

Motivation As of SAP NetWeaver 2004, you can save data as shared objects in shared memory, across different programs and even different user sessions. Accordingly, you can create applications in which users write data to this area. Other users can then read this data later. The potential uses for shared objects are as follows: ●

Saving a catalog An “author” writes the catalog to the shared objects area. Many users can then access this catalog at the same time.



Saving a shopping cart The buyer fills the shopping cart and the seller reads the filled shopping cart later.

448

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Shared Memory

Figure 161: Memory Model of an Application Server

Shared memory is a memory area on an application server that the ABAP programs running on the same server can access. Before SAP introduced shared objects, ABAP statements had to use the EXPORT and IMPORT statements with the SHARED BUFFER and SHARED MEMORY additions to access this memory area. Instances of classes were active exclusively in the internal session of an ABAP program. With the introduction of shared objects in SAP NetWeaver 2004, shared memory has been enhanced with Shared Objects Memory, where the user can save shared objects. You can save shared objects in areas of shared memory.

Note: Instances of classes can be saved. It is not yet possible to save any data objects as shared objects. However, you can save data objects apart from reference variables as attributes of classes.

© Copyright . All rights reserved.

449

Unit 10: Program Calls and Memory Management

Access Shared Objects

Figure 162: Accessing Shared Objects

The figure above explains how a shared object is being viewed by two user sessions simultaneously.

Shared Objects The following are important points about shared objects: ●

Cross-program buffering of data that is read often, but rarely written.



Concurrent read accesses are supported by shared objects.



Access is controlled by a lock mechanism.



Data is saved as attributes of objects.



Memory bottlenecks result in runtime errors and you need to identify them.

The write accesses should not be frequent because writing data to the shared objects area is performance intensive. Specifically, you want to optimize runtime, which would be lost if write access were more frequent.

450

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Note: SAP also uses shared objects in SAP NetWeaver 2004. For example, this technique is used to navigate in the ABAP Workbench. In addition to saving memory which is around 3 MB per user logon, navigation during the first access is faster by up to a factor of 100. A prerequisite for saving an object in shared memory is that you need to define the class of the object with the SHARED MEMORY ENABLED addition of the CLASS statement. Also, you can select the SHARED MEMORY ENABLED attribute in the CLASS BUILDER. 

Areas and Area Instances

Figure 163: Areas and Area Instances

An area is the template for area instances in shared memory. One area can generate several area instances, which differ by name. In addition, an area instance can have several versions which differ in their version IDs or version numbers. In the simplest case, without version management, an area instance consists of a single area instance version.

© Copyright . All rights reserved.

451

Unit 10: Program Calls and Memory Management

Area Classes and Area Handles

Figure 164: Creating an Area

You define an area in transaction SHMA. This creates a global, final area class of the same name. This is a subclass of CL_SHM_AREA. In an ABAP program, you can access the area exclusively using methods of the generated area class.

Hint: As the area and area class have the same name, it is advised to name the area according to the naming conventions for classes - ZCL_*, for example, in the customer namespace. You can use static methods (Attach methods) of an area class to attach an ABAP program, or its internal session where the system processes the ABAP program, to an area instance in shared memory. When you attach an ABAP program, an instance of the area class is created as an area handle. The figure also illustrates another class, which is the area root class. You can create any number of objects in an area instance, depending on your specific program. You access these objects uniformly through the instance of the area root class.

Note: You limit yourselves to two classes in a specific example.

452

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Example Application

Figure 165: Example Application

In this lesson, you develop a simple catalog application as an example. You want to use shared objects to create a catalog of flight dates, where the users can select any flight quickly. Access Areas

Figure 166: Accessing Areas

© Copyright . All rights reserved.

453

Unit 10: Program Calls and Memory Management

The figure highlights the fact that any programs can access objects in the shared objects memory. In this case, two applications, which run in different user sessions, access objects in the same area. For the example application, the requirements are as follows: Creating an area





Developing a program to create an area instance



Developing a program to read data from the area

Shared Memory Area – Definition

Figure 167: Area Management

You save shared objects in areas of shared memory. You use transaction SHMA to create and manage areas and their attributes.

Hint: Note that you have to call transaction code SHMA directly in SAP NetWeaver 2004, because it has not been added to the menu tree yet. Call transaction code SHMA and enter the name of the area. The usual namespace rules apply, which means the area name has to start with Y or Z in the customer system. The system also supports namespaces containing slashes.

Hint: Note that, for this area, the system generates an identically named global and final area class as a subclass of CL_SHM_AREA. Therefore, it is advised to choose the area name wisely, as shown in the example. In an ABAP program, an area is accessed exclusively using methods of the generated area class.

454

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Maintenance of Areas

Figure 168: Maintaining Areas

After you choose one of the pushbuttons Create, Change or Display, the system displays the maintenance screen for areas. The system has linked each area with a global area root class, whose attributes can contain proprietary data and references to other shared memory-enabled classes. You have to assign the area root class to an area when you maintain it. If an area instance version is not empty, it has to contain at least an instance of the area root class as its root object, which the system uses to reference other objects. When you generate the area class, the system generates and types a ROOT attribute with the static type of the area root class. Important terms for creating an area are as follows: ● Client-dependent area Areas, and thus the objects within an area, do not have a client ID by default. You can however specify an area as client-dependent. In client-dependent areas, the methods of the area class for accessing an area instance refer to the active client by default. You can use the optional importing parameter CLIENT to access another client explicitly. ●

Transactional area An area instance version of a transactional area is not active immediately after you remove a change lock with the DETACH_COMMIT method. It is not active until the next database commit. This is particularly helpful in implementing shopping carts in the shared objects memory.

© Copyright . All rights reserved.

455

Unit 10: Program Calls and Memory Management

Shared Memory Area – Write Access

Figure 169: Before Creating an Area Instance

You have defined an area. You have also created the classes that will be instantiated. Now, you examine the statements that can be used to create an area instance. You continue to use the previous example. When you create an area, the system creates a global final class with the same name. To set up an area or access an existing area, you need a reference variable that you can type with the generated area class. This reference serves as a handle for accessing the area.

456

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Area Instance Creation

Figure 170: Area Instance Creation

When you instantiate the area class, the system creates an instance of the area in shared memory. The program has a handle for this instance of the area. It performs all future operations using this handle. Object Generation in Shared Memory

Figure 171: Object Generation in Shared Memory

© Copyright . All rights reserved.

457

Unit 10: Program Calls and Memory Management

Once you create the area instance, you can create the objects in the shared objects memory. To do so, use the AREA HANDLE addition for the CREATE OBJECT statement. This statement informs the system about the area instance where it should create the objects. Object Generation in Shared Memory II

Figure 172: Object Generation in Shared Memory II

The figure illustrates how you can instantiate both objects from within the program. Alternatively, you can instantiate the root object from within the program. You can create the other objects in this area instance from the constructor of the root without assigning references (in this case).

458

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Root Object Setting

Figure 173: Root Object Setting

To be able to address the objects that you create in the area instance, assign the root object to the ROOT attribute of the area handle. To do so, use the SET_ROOT method of the area handle. As a consequence, any program of any application can access this area. To do so, the application merely has to fetch a reference to the area instance, and can then immediately access the objects contained in that area instance.

© Copyright . All rights reserved.

459

Unit 10: Program Calls and Memory Management

Write Lock Releasing

Figure 174: Write Lock Releasing

Read access of an area instance is not possible until the release of write lock. For the read access, use the DETACH_COMMIT method, which inherits the area class from class CL_SHM_AREA.

Shared Memory Area – Read Access

Figure 175: Accessing an Existing Object in Shared Memory

460

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Once an area instance has been set up, other users and applications can access it. The reading programs have to implement the following steps: 1. The read program first needs a reference variable that is you type with the area class. This reference variable serves as a handle for the area instance access. 2. The program obtains the handle for the area instance using method ATTACH_FOR_READ, which class CL_SHM_AREA provides. This sets a read lock that prevents the system to erase the area instance during the access. 3. The objects in this area instance are now accessible by always using the area handle. Read Lock Cancellation

Figure 176: Read Lock Cancellation

Once the read activity is complete, the application releases the read lock using the method DETACH of the area handle. The application automatically releases the read lock when the internal session is closed after a DETACH statement.

© Copyright . All rights reserved.

461

Unit 10: Program Calls and Memory Management

Shared Memory Area – Versioning

Figure 177: Setting a Read Lock on the Active Version

When you create an area, you can specify that the system allows several versions of an area instance. To determine what exactly these area instance versions mean, you need to examine an example. A normal state is when an area instance has been set up. Once the setup is complete using method DETACH_COMMIT, and the system sends a database commit, the area instance version is active.

462

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Version Being Set Up

Figure 178: Version Being Set Up

If the NUMBER OF VERSIONS attribute of the area is set appropriately, additional versions of the area instance can exist in addition to the active version. When a new catalog is being set up, several temporary versions of the same area instance exist concurrently. As soon as an application sets a change lock for an area instance, a “version being set up” is created and exists in parallel to the active version.

© Copyright . All rights reserved.

463

Unit 10: Program Calls and Memory Management

Write Complete – Previous Version is Outdated

Figure 179: Write Complete – Previous Version is Outdated

If you complete the setup of the new version during a read access of the currently active version, the version being set up becomes active. The previously active version is given the attribute OUTDATED. New Read Locks for the New Active Version

Figure 180: New Read Locks for the New Active Version

464

© Copyright . All rights reserved.

Lesson: Using Shared Objects

The read locks for the outdated version remain until the read operations are complete. In contrast, new read locks for the area instance are always set for the active version. Therefore, two different readers can produce two different read results in this case. No More Read Blocks for Outdated Version – Version Expired

Figure 181: No More Read Blocks for Outdated Version – Version Expired

When you remove the last existing read lock from outdated version, the outdated version expires. The garbage collector then deletes the expired version. You cannot set any read locks for versions that expire, or use them to determine the number of versions. This is important if the system restricts the number of area instance versions.

© Copyright . All rights reserved.

465

Unit 10: Program Calls and Memory Management

New Read Locks for Active Version

Figure 182: New Read Locks for Active Version

New read locks are always set for the active version. There can only be one active version for each area instance. Depending on the maximum number of versions, several outdated versions for which read locks are still set can exist in parallel to the new version.

466

© Copyright . All rights reserved.

Unit 10 Exercise 25 Use Shared Objects

Business Example You want to run an Internet shop based on an SAP system. To give your Internet customers the fastest possible access to your catalog, you save it in the shared objects memory. Write program to manage and describe the catalog and develop a test application to read the data. Template None Solution CL_BC402_SHS_ROOT (global class) CL_BC402_SHS_CATALOG (global class) BC402_SHS_WRITE_CATALOG (executable program) BC402_SHS_READ_CATALOG (executable program) Create a shared objects area, write and read data on this area. Task 1 Create an area in shared objects memory (suggested name: ZCL_BC402_##_AREA, where ## is your group number). 1. Use transaction SHMA to create an area in shared memory. This area should have the following attributes: ●

Client-specific Area



With Versioning



Displacement not Possible

The system automatically prompts you to specify a root class. Create an area root class (suggested name: ZCL_BC402_##_ROOT). 2. Implement the area root class. It should merely contain a reference to the catalog class that you will create in the next exercise task. Task 2 Create a global class where the catalog data is to be saved (suggested name: CL_BC402_##_CATALOG). This class requires a method for writing the catalog data and another method for retrieving the data. It also requires a global attribute and an internal table that saves the catalog data.

© Copyright . All rights reserved.

467

Unit 10: Program Calls and Memory Management

1. Create the global class for the catalog data. Note that this class has to be shared memoryenabled. 2. Create a private instance attribute in the class (suggested name: MT_CATALOG). Enter it with a table type that has structure SDYN_CONN as a line type. 3. Create a public instance method to fill the catalog (suggested name: FILL_CATALOG). This method requires an importing parameter that will be given the internal table with data. Implement the method. 4. Create a second public instance method that can be used to answer flight date queries (suggested name: GET_FLIGHTS). This method requires one importing parameter each for the departure and destination cities, as well as two additional parameters for the different flight dates. The method also needs an exporting parameter that returns the matching flights. Implement the method. Task 3 Create an executable program that builds the area in shared objects memory (suggested name: ZBC402_##_WRITE_CATALOG). This program is also supposed to read the catalog data from the database and pass it on to the appropriate class. 1. Create an executable program. 2. Define three reference variables, one each for the area handle, the area root class, and the catalog class. 3. Create an area, an instance of the catalog class, and an instance of the area root class. Set up the area. Read the necessary catalog data from tables SPFLI and SFLIGHT. 4. Don’t forget to delete the write lock after the data is written successfully. 5. Execute the program and then use the Shared Objects Monitor to examine the shared memory area. Task 4 Implement a read program to read data from the area you just created (suggested name: ZBC402_##_READ_CATALOG). Output the data in a simple user dialog (using the provided function module BC402_DISPLAY_TABLE, for example). 1. Create an executable program. 2. Define a selection screen in which the user can enter the departure and destination cities. The user should also be able to enter an earliest and latest possible flight date. 3. Make sure the data is read from the catalog object. Output the data in the user dialog.

468

© Copyright . All rights reserved.

Unit 10 Solution 25 Use Shared Objects

Business Example You want to run an Internet shop based on an SAP system. To give your Internet customers the fastest possible access to your catalog, you save it in the shared objects memory. Write program to manage and describe the catalog and develop a test application to read the data. Template None Solution CL_BC402_SHS_ROOT (global class) CL_BC402_SHS_CATALOG (global class) BC402_SHS_WRITE_CATALOG (executable program) BC402_SHS_READ_CATALOG (executable program) Create a shared objects area, write and read data on this area. Task 1 Create an area in shared objects memory (suggested name: ZCL_BC402_##_AREA, where ## is your group number). 1. Use transaction SHMA to create an area in shared memory. This area should have the following attributes: ●

Client-specific Area



With Versioning



Displacement not Possible

The system automatically prompts you to specify a root class. Create an area root class (suggested name: ZCL_BC402_##_ROOT). a) Follow the instructor’s demonstration. 2. Implement the area root class. It should merely contain a reference to the catalog class that you will create in the next exercise task. a) See the source code excerpt from the model solution. Task 2 Create a global class where the catalog data is to be saved (suggested name: CL_BC402_##_CATALOG). This class requires a method for writing the catalog data and another

© Copyright . All rights reserved.

469

Unit 10: Program Calls and Memory Management

method for retrieving the data. It also requires a global attribute and an internal table that saves the catalog data. 1. Create the global class for the catalog data. Note that this class has to be shared memoryenabled. a) Create the class in the CLASS BUILDER. Use the sample solution as a guide. 2. Create a private instance attribute in the class (suggested name: MT_CATALOG). Enter it with a table type that has structure SDYN_CONN as a line type. a) See the source code excerpt from the model solution. 3. Create a public instance method to fill the catalog (suggested name: FILL_CATALOG). This method requires an importing parameter that will be given the internal table with data. Implement the method. a) See the source code excerpt from the model solution. 4. Create a second public instance method that can be used to answer flight date queries (suggested name: GET_FLIGHTS). This method requires one importing parameter each for the departure and destination cities, as well as two additional parameters for the different flight dates. The method also needs an exporting parameter that returns the matching flights. Implement the method. a) See the source code excerpt from the model solution. Task 3 Create an executable program that builds the area in shared objects memory (suggested name: ZBC402_##_WRITE_CATALOG). This program is also supposed to read the catalog data from the database and pass it on to the appropriate class. 1. Create an executable program. a) Carry out this step in the usual manner. 2. Define three reference variables, one each for the area handle, the area root class, and the catalog class. a) See the source code excerpt from the model solution. 3. Create an area, an instance of the catalog class, and an instance of the area root class. Set up the area. Read the necessary catalog data from tables SPFLI and SFLIGHT. a) See the source code excerpt from the model solution. 4. Don’t forget to delete the write lock after the data is written successfully. a) See the source code excerpt from the model solution. 5. Execute the program and then use the Shared Objects Monitor to examine the shared memory area. a) Execute the program and then run transaction SHMM to examine the details of the shared memory area instance.

470

© Copyright . All rights reserved.

Lesson: Using Shared Objects

Task 4 Implement a read program to read data from the area you just created (suggested name: ZBC402_##_READ_CATALOG). Output the data in a simple user dialog (using the provided function module BC402_DISPLAY_TABLE, for example). 1. Create an executable program. a) Carry out this step in the usual manner. 2. Define a selection screen in which the user can enter the departure and destination cities. The user should also be able to enter an earliest and latest possible flight date. a) See the source code excerpt from the model solution. 3. Make sure the data is read from the catalog object. Output the data in the user dialog. a) See the source code excerpt from the model solution. Class CL_BC402_SHS_CATALOG: Implementation

METHOD fill_catalog. gt_catalog = it_catalog. ENDMETHOD. METHOD get_flights. FIELD-SYMBOLS: TYPE sdyn_conn. LOOP AT gt_catalog ASSIGNING WHERE cityfrom cityto fldate fldate

= = > <

iv_from_city AND iv_to_city AND iv_earliest AND iv_latest.

APPEND TO et_flights. ENDLOOP. ENDMETHOD.

Program BC402_SHS_WRITE_CATALOG

REPORT

bc402_shs_write_catalog.

DATA: go_handle go_root

TYPE REF TO cl_bc402_shs_area, TYPE REF TO cl_bc402_shs_root,

© Copyright . All rights reserved.

471

Unit 10: Program Calls and Memory Management

go_catalog TYPE REF TO cl_bc402_shs_catalog, gt_flights TYPE

bc402_t_sdynconn.

START-OF-SELECTION. go_handle = cl_bc402_shs_area=>attach_for_write( ). CREATE OBJECT go_root AREA HANDLE go_handle. CREATE OBJECT go_catalog AREA HANDLE go_handle. go_root->mo_catalog = go_catalog. go_handle->set_root( root = go_root ). SELECT * FROM spfli JOIN sflight ON spfli~carrid = sflight~carrid AND spfli~connid = sflight~connid INTO CORRESPONDING FIELDS OF TABLE gt_flights. go_handle->root->mo_catalog->fill_catalog( it_catalog = gt_flights ). go_handle->detach_commit( ).

Program BC402_SHS_READ_CATALOG

REPORT

bc402_shs_read_catalog.

DATA: go_handle gt_flights gs_flight

TYPE REF TO TYPE LIKE LINE OF

cl_bc402_shs_area, bc402_t_sdynconn, gt_flights,

gv_startdate TYPE sydatum, gv_enddate TYPE sydatum. PARAMETERS: pa_from pa_to SELECT-OPTIONS: so_date

TYPE spfli-cityfrom, TYPE spfli-cityto. FOR sy-datum NO-EXTENSION.

AT SELECTION-SCREEN. READ TABLE so_date INDEX 1. IF so_date IS INITIAL. so_date-low = sy-datum. so_date-high = sy-datum + 365. ENDIF.

472

© Copyright . All rights reserved.

Lesson: Using Shared Objects

gv_startdate = sy-datum. gv_enddate = sy-datum + 365. IF so_date-low > sy-datum. gv_startdate = sy-datum. ENDIF. IF so_date-high < gv_enddate. gv_enddate = so_date-high. ENDIF. START-OF-SELECTION. go_handle = cl_bc402_shs_area=>attach_for_read( ). go_handle->root->mo_catalog->get_flights( EXPORTING iv_from_city = pa_from iv_to_city = pa_to iv_earliest = gv_startdate iv_latest = gv_enddate IMPORTING et_flights = gt_flights ). go_handle->detach( ). CALL FUNCTION 'BC402_DISPLAY_TABLE' CHANGING ct_table = gt_flights.

© Copyright . All rights reserved.

473

Unit 10: Program Calls and Memory Management

LESSON SUMMARY You should now be able to:

474



Explain shared objects



Use shared objects

© Copyright . All rights reserved.

Unit 10 Learning Assessment

1. Shared memory is a memory area on an application server that the ABAP programs running on that server can access. Determine whether this statement is true or false. X

True

X

False

2. Method __________ of the area handle is available for the application to release the read lock. Choose the correct answer. X

A DETACH_COMMIT

X

B OUTDATED

X

C DETACH

© Copyright . All rights reserved.

475

Unit 10 Learning Assessment - Answers

1. Shared memory is a memory area on an application server that the ABAP programs running on that server can access. Determine whether this statement is true or false. X

True

X

False

2. Method __________ of the area handle is available for the application to release the read lock. Choose the correct answer.

476

X

A DETACH_COMMIT

X

B OUTDATED

X

C DETACH

© Copyright . All rights reserved.

UNIT 11

Dynamic Programming

Lesson 1 Using Generic Data Types Exercise 26: Use Dynamically Typed Field Symbols in Dynamic SQL Statements Exercise 27: Access Structure Components Dynamically

478 485 495

Lesson 2 Describing Data Types, Data Objects, and Objects at Runtime Exercise 28: Provide Column Headers Using Runtime Type Identification

504 517

Lesson 3 Creating Data Types, Data Objects, and Objects at Runtime Exercise 29: Create Data Objects at Runtime Exercise 30: Create Data Types at Runtime with Runtime Type Creation (RTTC)

528 535 545

UNIT OBJECTIVES ●

Explain generic data types of ABAP



Use generic data types



Access data objects dynamically



Use generically typed data references



Explain the principle of RTTI



Describe data types and data objects at runtime



Describe object types and objects at runtime



Create objects (instances) at runtime



Create data objects at runtime



Create data types at runtime

© Copyright . All rights reserved.

477

Unit 11 Lesson 1 Using Generic Data Types

LESSON OVERVIEW This lesson discusses how to use generic data types in ABAP for dynamic programming. It also discusses the constraints posed on generic data references by the ABAP syntax and how these constraints affect generic data use. Business Example You need to develop a flexible application. You therefore want to find out about the generic data types in ABAP and learn how to type parameters, field symbols, and data references generically. For this reason, you require the following knowledge: ●







An understanding of generic types and their uses An understanding of how to use generically typed parameters, field symbols, and data references An understanding of how to use field symbols to access data objects dynamically An understanding of how to use field symbols to access attributes and structure components dynamically

LESSON OBJECTIVES After completing this lesson, you will be able to:

478



Explain generic data types of ABAP



Use generic data types



Access data objects dynamically



Use generically typed data references

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

ABAP Built-In Generic Data Types

Figure 183: Generic ABAP Data Types

The figure illustrates the predefined generic data types supported by ABAP syntax. In addition to complete data types, ABAP also features a number of generic data types. In contrast to complete types, you cannot use generic types to define the properties of data objects. You only use generic types to type formal parameters and field symbols. Note: Currently, the two built-in types, ... TYPE REF TO OBJECT and ... TYPE REF TO DATA are the only types available for typing reference variables generically. Generic ABAP Data Types – Internal Tables

Figure 184: Generic ABAP Data Types – Internal Tables

© Copyright . All rights reserved.

479

Unit 11: Dynamic Programming

Hint: Most generic types, such as clike, csequence, numeric, simple, and xsequence, are available as of SAP Web AS 6.10. Generic type decfloat is available as of SAP NetWeaver 7.0 EhP 2. The figure shows generic ABAP data types, which are compatible with the set of ABAP types. When you call a procedure, the system checks whether the type of the actual parameter is compatible with the type of the formal parameter. When you assign a generically typed field symbol, the syntax check tests whether the type of the data object is compatible with the generic type of the field symbol.

Note: The DATA type behaves in the same way as ANY. The differentiation is purely theoretical at this point. In the future, however, reference variables with type TYPE REF TO ANY to point data objects or instances of classes might be possible. The ANY TABLE, INDEX TABLE, SORTED TABLE, and other types are special generic data types that are only compatible with internal tables. You can restrict them to internal tables with a specific table type. However, the line type and key definition remain open.

Freely Defined Generic Table Types

Figure 185: Generic Table Types – User-Defined

In addition to these built-in generic table types, ABAP also contains generic table types that developers create as generic types. These generic table types are created either in the ABAP Dictionary or in the program source code, with the TYPES statement. The figure shows an example of locally defined generic table types. In these generic table types, you define the line type, but the table type and key definition remain open.

480

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

Note: To create appropriate generic types in the ABAP Dictionary, check the corresponding options under Access and Key. Apart from the generic table types, there are no user-defined generic table types in ABAP.

Generically Typed Parameters

Figure 186: Problems When Parameters Are Too General

When you generically type formal parameters of a procedure, such as subroutine, function module, or method, the procedure becomes more flexible. Use syntax check to ensure that the procedure handles the different types. The syntax check ensures that the system passes only actual parameters with compatible types to generically typed formal parameters. When generically typed parameters are addressed in ABAP statements, wait until runtime to determine whether the type of underlying data object or its current content is logical in the respective operand position. If conflicts occur, the system raises runtime errors that are not caught in most cases. The figure shows an example. If you assign an internal table or a structure that is not flat and character-type to a parameter, the WRITE statement raises an uncatchable exception, OBJECTS_NOT_CHARCONV. The syntax check helps avoid such runtime errors, particularly in operand positions that only allow internal tables, such as SELECT ... INTO TABLE ... and LOOP AT TABLE .... The syntax only accepts generic table types in these operand positions. Therefore, ensure that an internal table comes after the formal parameter. To avoid syntax errors and runtime errors, select generic types that are specific enough to be used with all compatible types in the desired operand position.

© Copyright . All rights reserved.

481

Unit 11: Dynamic Programming

Type Precisely to Avoid Errors

Figure 187: Avoiding Errors by Typing as Precisely as Possible

If you use the generic type SIMPLE, the WRITE statement does not cause runtime errors. You can convert all data types that are compatible with SIMPLE to a character string. The syntax errors are corrected because parameter it_data now accepts only internal tables because of its type, ANY TABLE.

Hint: A runtime error can still occur if the method contains an index access to it_data, specifically, if the actual parameter is a hashed table. Use the generic type INDEX TABLE to restrict the formal parameter even further.

482

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

Generically Typed Field Symbols

Figure 188: Example – Generic Field Symbol in Dynamic SELECT

Field symbols are pointers that you assign to data objects dynamically. While using the field symbol in an ABAP statement, dynamically define the specific data object that the field symbol refers to. If the field symbol is fully typed, then all potential data objects have the same type, which restricts the possible uses of field symbols significantly. Generic typing enables the field symbol to refer to data objects with different types. As a result, you can address different data objects in the same operand position of an ABAP statement. The figure shows an example of how to use a field symbol in a dynamic SELECT statement. To command the program to access one of two database tables, SCARR or SBOOK, depending on the content of data object lv_table_name, program a dynamic SELECT statement. To ensure that the line type of the internal table matches the field list of the database table, use a generically typed field symbol as a target that points to internal table lt_scarr or lt_sbook as required.

Hint: The field symbol cannot have type ANY. If you assign this type to the two internal tables without any problems, it causes a syntax error when used in the SELECT statement.

© Copyright . All rights reserved.

483

Unit 11: Dynamic Programming

Note: This example is only dynamic to an extent because data objects needs to be defined statically.

Type Casting for Field Symbols

Figure 189: Type Casting for Field Symbols

To remove the restrictions of the data object’s original type, use the CASTING addition to assign a data object to a field symbol. This field symbol has a different type. The data object is then interpreted as though it has the data type of the field symbol. To access the data object using the field symbol as if the object has an explicitly specified type, use the CASTING TYPE addition. The CASTING TYPE addition is used to assign a data object to a field symbol. This field symbol has a different type. In the figure, note that the system field is an elementary character-type component of length 8.

484

© Copyright . All rights reserved.

Unit 11 Exercise 26 Use Dynamically Typed Field Symbols in Dynamic SQL Statements

Business Example You need to develop a simple program that displays the contents of any database table. Find out about the options available in dynamic programming. Define the database table in a SELECT statement dynamically, and use a generically typed field symbol to specify the target range of a SELECT statement dynamically. Task 1 Copy program BC402_DYS_DYN_CALL or your own program ZBC402_##_DYN_CALL and name it ZBC402_##_DYN_SQL, where ## is your group number. Familiarize yourself with the program and how it works. 1. Copy the program and all its subcomponents. 2. Activate and test the program. Analyze the source code. How is the data read from the database and into which data objects is it filled?

Task 2 Replace the two SELECT statements with a single SELECT statement after the ENDCASE statement. Specify the table name as a character-type data object. In addition, use a generically typed field symbol as the target range (INTO clause) to which you dynamically assign a suitable data object. 1. Define a character-type data object for the table name (suggested name is gv_tabname). Fill the data object with the respective table names in the WHEN blocks. 2. Create a field symbol (suggested name is ) whose type is assigned as either data object gt_conn or gt_cust. 3. Why is type ANY not suitable? 4. Assign the field symbol to the respective internal tables in the WHEN blocks, the ones you want to fill in the generic SELECT statement. 5. Move one of the two SELECT statements from the WHEN block to after the ENDCASE statement and delete the other one. Make the remaining database access dynamic. Replace the static table name with data object gv_tabname and replace the target range (internal table) with the field symbol.

© Copyright . All rights reserved.

485

Unit 11: Dynamic Programming

Task 3 Optional Catch the specific runtime errors that occur when using dynamic SQL statements. 1. Read the keyword documentation to find out about the exceptions that occur when using dynamic SQL statements. Implement exception handling with TRY... CATCH ... ENDTRY. Either implement a separate CATCH block for each of the exception classes or use a single CATCH block for the shared superclass. If an error occurs, respond with error message 061 from message class BC402.

486

© Copyright . All rights reserved.

Unit 11 Solution 26 Use Dynamically Typed Field Symbols in Dynamic SQL Statements

Business Example You need to develop a simple program that displays the contents of any database table. Find out about the options available in dynamic programming. Define the database table in a SELECT statement dynamically, and use a generically typed field symbol to specify the target range of a SELECT statement dynamically. Task 1 Copy program BC402_DYS_DYN_CALL or your own program ZBC402_##_DYN_CALL and name it ZBC402_##_DYN_SQL, where ## is your group number. Familiarize yourself with the program and how it works. 1. Copy the program and all its subcomponents. a) Perform this step as usual. 2. Activate and test the program. Analyze the source code. How is the data read from the database and into which data objects is it filled? a) The data is read from the database in static SELECT statements. In the process, one of two statically defined internal tables is filled.

Task 2 Replace the two SELECT statements with a single SELECT statement after the ENDCASE statement. Specify the table name as a character-type data object. In addition, use a generically typed field symbol as the target range (INTO clause) to which you dynamically assign a suitable data object. 1. Define a character-type data object for the table name (suggested name is gv_tabname). Fill the data object with the respective table names in the WHEN blocks. a) See the source code excerpt from the model solution. 2. Create a field symbol (suggested name is ) whose type is assigned as either data object gt_conn or gt_cust. a) See the source code excerpt from the model solution. 3. Why is type ANY not suitable?

© Copyright . All rights reserved.

487

Unit 11: Dynamic Programming

a) The field symbol should be specified after INTO TABLE in the SELECT statement. The syntax check only allows generic values here, with at least type ANY TABLE. 4. Assign the field symbol to the respective internal tables in the WHEN blocks, the ones you want to fill in the generic SELECT statement. a) See the source code excerpt from the model solution. 5. Move one of the two SELECT statements from the WHEN block to after the ENDCASE statement and delete the other one. Make the remaining database access dynamic. Replace the static table name with data object gv_tabname and replace the target range (internal table) with the field symbol. a) See the source code excerpt from the model solution.

Task 3 Optional Catch the specific runtime errors that occur when using dynamic SQL statements. 1. Read the keyword documentation to find out about the exceptions that occur when using dynamic SQL statements. Implement exception handling with TRY... CATCH ... ENDTRY. Either implement a separate CATCH block for each of the exception classes or use a single CATCH block for the shared superclass. If an error occurs, respond with error message 061 from message class BC402. a) See the source code excerpt from the model solution. REPORT

bc402_dys_dyn_sql MESSAGE-ID bc402.

TYPE-POOLS: abap. DATA: gt_cust gt_conn

TYPE ty_customers, TYPE ty_connections.

DATA: gv_methname TYPE string, gt_parmbind TYPE abap_parmbind_tab, gs_parmbind TYPE abap_parmbind. DATA: gv_tabname

TYPE string.

FIELD-SYMBOLS: TYPE ANY TABLE. SELECTION-SCREEN COMMENT 1(80) text-sel. PARAMETERS: pa_xconn TYPE xfeld RADIOBUTTON GROUP tab DEFAULT 'X', pa_xcust TYPE xfeld RADIOBUTTON GROUP tab . PARAMETERS: pa_nol TYPE i DEFAULT '100'.

488

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

START-OF-SELECTION. * specific part *------------------------------------------* CASE 'X'. WHEN pa_xconn. gv_tabname = 'SPFLI'. ASSIGN gt_conn TO . gv_methname = 'WRITE_CONNECTIONS'. gs_parmbind-name = 'IT_CONN'. GET REFERENCE OF gt_conn INTO gs_parmbind-value. INSERT gs_parmbind INTO TABLE gt_parmbind. WHEN pa_xcust. gv_tabname = 'SCUSTOM'. ASSIGN gt_cust TO . gv_methname = 'WRITE_CUSTOMERS'. gs_parmbind-name = 'IT_CUST'. GET REFERENCE OF gt_cust INTO gs_parmbind-value. INSERT gs_parmbind INTO TABLE gt_parmbind. ENDCASE. * dynamic part *---------------------------------------------* TRY.

SELECT * FROM (gv_tabname) INTO TABLE UP TO pa_nol ROWS. CATCH cx_sy_dynamic_osql_error. MESSAGE e061. ENDTRY. TRY.

CALL METHOD cl_bc402_utilities=>(gv_methname) PARAMETER-TABLE gt_parmbind.

CATCH cx_sy_dyn_call_error. MESSAGE e060. ENDTRY.

© Copyright . All rights reserved.

489

Unit 11: Dynamic Programming

Dynamic Access to Data Objects

Figure 190: Dynamic Access to Data Objects

In most ABAP statements, do not replace data objects in operand positions directly with character-type data objects in parentheses. Instead, use the ASSIGN statement for the data object to which you need to assign the field symbol. Use this approach to address the data object dynamically by its name. Assign a generically typed field symbol to the data object using the syntax shown in the figure, and then use the field symbol in the ABAP statement. You can also use easier, less error-prone alternatives to access attributes and structure components.

490

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

Dynamic Access to Instance Attributes and Class Attributes

Figure 191: Dynamic Access to Object Attributes and Class Attributes

In addition to using the full identifier for dynamic access to attributes of classes and instance,  use another variant to specify the attribute name solely with a character-type data object. Specify the object reference and component selector statically. You also specify the class name for static attributes dynamically, if necessary. This syntax is similar to that for dynamic method calls.

Hint: Because the syntax check supports the static part of the statement, these variants are less error-prone and are therefore preferred.

© Copyright . All rights reserved.

491

Unit 11: Dynamic Programming

Dynamic Access to Structure Components

Figure 192: Dynamic Access to Structure Components

Use a special variant of the ASSIGN statement to access structure components dynamically. You specify the structure statically or through a separate field symbol in the ASSIGN COMPONENT ... OF STRUCTURE ... statement. Address the components either by name or by position (number) within the structure. Hint: Because the syntax check supports the static part of the statement, these variants are less error-prone and are therefore preferred. Because the system addresses the components of a structure by their positions in sequence, you can process any structure completely, component by component.

492

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

Full Processing of Any Non-Nested, Flat Structure

Figure 193: Full Processing of Any Non-Nested, Flat Structure

Caution: In the figure, an uncatchable ASSIGN_TYPE_CONFLICT runtime error occurs if the transferred structure contains a component that is incompatible with the generic SIMPLE type of the field symbols. Similarly, a runtime error occurs during the WRITE statement when you type the field symbol with ANY.

© Copyright . All rights reserved.

493

Unit 11: Dynamic Programming

494

© Copyright . All rights reserved.

Unit 11 Exercise 27 Access Structure Components Dynamically

Business Example You need to develop a simple program that displays the contents of any database table. You therefore want to find out about the options available in dynamic programming. To implement a generic method that enables you to output the contents of any table in a list (provided the line type of the internal table has a flat structure), replace the dynamic call of two specific methods with a static call of a generic method. Use generically typed interface parameters, generically typed field symbols, and access structure components dynamically. Task 1 Copy global class CL_BC402_DYT_GEN_TYPES and name it ZCL_BC402_##_GEN_TYPES, where ## is your group number. Familiarize yourself with the class signature. 1. Copy the global class. 2. Analyze the class signature. Which methods are defined? What is their purpose? 3. Which parameters do these methods have? How are the parameters typed?

Task 2 Implement method write_any_struct, and output all components of structure gs_struct individually with a WRITE statement by programming a loop in which you access all the components in structure gs_struct consecutively. 1. Create a field symbol (suggested name is ) that has a generic type that allows assignment of any flat components of the structure. 2. Program a DO loop. Use the sy-index loop counter to access all components of gs_struct consecutively with the field symbol. 3. Check whether the field symbol assignment was successful. If it was, output the component with a WRITE statement. Otherwise, exit the loop.

Task 3 Implement method write_any_table. Display the contents of internal table it_table in a list by lines by programming a loop over internal table gt_table. Call your previously implemented method, write_any_struct, for each line.

© Copyright . All rights reserved.

495

Unit 11: Dynamic Programming

1. Create a field symbol (suggested name is ) that has a generic type  that allows assignment of a line of generic internal table it_table. 2. Program a LOOP over internal table it_table. Assign the lines in the internal table to field symbol consecutively. 3. Call method write_any_struct for each line.

Task 4 Copy program BC402_DYS_DYN_SQL or your own program ZBC402_##_DYN_SQL and name it ZBC402_##_GEN_TYPES, where ## is your group number. Familiarize yourself with the program and how it works. 1. Copy the program and all its subcomponents. 2. Activate and test the program. Analyze the source code.

Task 5 Replace the dynamic method call at the end of the program with a call of your new method, write_any_table. Remove all parts of the source code you no longer need, or flag them as comments. 1. Delete the dynamic method call or flag it as a comment. In its place, implement a call of method write_any_table. Give the method the generic field symbol that points to the internal table with the data. 2. Delete the definitions of the data objects that are needed for the dynamic method call or flag them as comments. 3. Activate and test the program.

496

© Copyright . All rights reserved.

Unit 11 Solution 27 Access Structure Components Dynamically

Business Example You need to develop a simple program that displays the contents of any database table. You therefore want to find out about the options available in dynamic programming. To implement a generic method that enables you to output the contents of any table in a list (provided the line type of the internal table has a flat structure), replace the dynamic call of two specific methods with a static call of a generic method. Use generically typed interface parameters, generically typed field symbols, and access structure components dynamically. Task 1 Copy global class CL_BC402_DYT_GEN_TYPES and name it ZCL_BC402_##_GEN_TYPES, where ## is your group number. Familiarize yourself with the class signature. 1. Copy the global class. a) Carry out this step as usual. 2. Analyze the class signature. Which methods are defined? What is their purpose? a) write_any_struct and write_any_table for list output of any flat structure or any internal table with flat line type. 3. Which parameters do these methods have? How are the parameters typed? a) The two parameters are gs_struct TYPE ANY and gt_struct TYPE ANY TABLE.

Task 2 Implement method write_any_struct, and output all components of structure gs_struct individually with a WRITE statement by programming a loop in which you access all the components in structure gs_struct consecutively. 1. Create a field symbol (suggested name is ) that has a generic type that allows assignment of any flat components of the structure. a) See the source code excerpt from the model solution. 2. Program a DO loop. Use the sy-index loop counter to access all components of gs_struct consecutively with the field symbol. a) See the source code excerpt from the model solution. 3. Check whether the field symbol assignment was successful. If it was, output the component with a WRITE statement. Otherwise, exit the loop.

© Copyright . All rights reserved.

497

Unit 11: Dynamic Programming

a) See the source code excerpt from the model solution.

Task 3 Implement method write_any_table. Display the contents of internal table it_table in a list by lines by programming a loop over internal table gt_table. Call your previously implemented method, write_any_struct, for each line. 1. Create a field symbol (suggested name is ) that has a generic type  that allows assignment of a line of generic internal table it_table. a) See the source code excerpt from the model solution. 2. Program a LOOP over internal table it_table. Assign the lines in the internal table to field symbol consecutively. a) See the source code excerpt from the model solution. 3. Call method write_any_struct for each line. a) See the source code excerpt from the model solution.

Task 4 Copy program BC402_DYS_DYN_SQL or your own program ZBC402_##_DYN_SQL and name it ZBC402_##_GEN_TYPES, where ## is your group number. Familiarize yourself with the program and how it works. 1. Copy the program and all its subcomponents. a) Perform this step as usual. 2. Activate and test the program. Analyze the source code. a) Perform this step as usual.

Task 5 Replace the dynamic method call at the end of the program with a call of your new method, write_any_table. Remove all parts of the source code you no longer need, or flag them as comments. 1. Delete the dynamic method call or flag it as a comment. In its place, implement a call of method write_any_table. Give the method the generic field symbol that points to the internal table with the data. a) See the source code excerpt from the model solution. 2. Delete the definitions of the data objects that are needed for the dynamic method call or flag them as comments. a) See the source code excerpt from the model solution. 3. Activate and test the program.

498

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

a) Perform this step as usual. Method write_any_struct (Class CL_BC402_DYS_GEN_TYPE) method WRITE_ANY_STRUCT. FIELD-SYMBOLS TYPE simple. NEW-LINE. DO. ASSIGN COMPONENT sy-index OF STRUCTURE is_struct TO . IF sy-subrc = 0. WRITE . ELSE. EXIT. ENDIF. ENDDO. endmethod. Method write_any_table (Class CL_BC402_DYS_GEN_TYPE) method WRITE_ANY_TABLE. FIELD-SYMBOLS: TYPE ANY. LOOP AT it_table ASSIGNING . write_any_struct( ). ENDLOOP. endmethod. Executable Program BC402_DYS_GEN_TYPES REPORT

bc402_dys_gen_types MESSAGE-ID bc402.

*TYPE-POOLS: abap. DATA: gt_cust gt_conn

TYPE ty_customers, TYPE ty_connections.

*DATA: * gv_methname TYPE string, * gt_parmbind TYPE abap_parmbind_tab, * gs_parmbind TYPE abap_parmbind. DATA: gv_tabname

TYPE string.

FIELD-SYMBOLS: TYPE ANY TABLE. SELECTION-SCREEN COMMENT 1(80) text-sel.

© Copyright . All rights reserved.

499

Unit 11: Dynamic Programming

PARAMETERS: pa_xconn TYPE xfeld RADIOBUTTON GROUP tab DEFAULT 'X', pa_xcust TYPE xfeld RADIOBUTTON GROUP tab . PARAMETERS: pa_nol TYPE i DEFAULT '100'. START-OF-SELECTION. * specific part *----------------------------------------------------* CASE 'X'. WHEN pa_xconn. gv_tabname = 'SPFLI'. ASSIGN gt_conn TO . WHEN pa_xcust. gv_tabname = 'SCUSTOM'. ASSIGN gt_cust TO . ENDCASE. * dynamic part *------------------------------------------------------* TRY.

SELECT * FROM (gv_tabname) INTO TABLE UP TO pa_nol ROWS. CATCH cx_sy_dynamic_osql_error. MESSAGE e061. ENDTRY. * * * * * * * *

TRY.

CALL METHOD cl_bc402_utilities=>(gv_methname) PARAMETER-TABLE gt_parmbind.

CATCH cx_sy_dyn_call_error. MESSAGE e060. ENDTRY. cl_bc402_dys_gen_types=>write_any_table( fs_table ).

500

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

Generically Typed Data References You can type reference variables generically. However, in contrast to field symbols, only the generic types DATA (for data references) and OBJECT (for object references) are available for reference variables. The use of generically typed reference variables is restricted in ABAP. With the exception of the ASSIGN statement, generically typed reference variables cannot be dereferenced directly in operand positions. The statement WRITE ref->* has incorrect syntax, for example, if the data reference has type TYPE REF TO DATA. Due to these restrictions, you use generic data references only where generic field symbols do not work.

Use Cases for Generically Typed Data References The options for addressing the contents of the referenced data object for references with type TYPE REF TO DATA are as follows: ●

In internal tables



During the dynamic generation of data objects using the CREATE DATA statement

Cast Assignment for Data References

Figure 194: Cast Assignment for Data References

To address the content of referenced data objects, use a fully typed data reference. The contents of the generic data reference are copied to the fully typed data reference. You can then dereference the complete data reference in any operand item.

© Copyright . All rights reserved.

501

Unit 11: Dynamic Programming

However, for this technique to work, the second reference variable needs to have the same type as the referenced data object. When you assign values between two reference variables with different types, you perform a cast assignment. It is similar to cast assignment between object references, which you learned about during object-oriented programming. As with object references, an up cast occurs when the target variable has a more general definition, and a down cast occurs when the target variable has a more specific type than the source variable. Accordingly, assignment from a generic data reference to a full reference is a down cast. While up casts to type TYPE REF TO DATA always work, the down cast must have the ?= cast operator to have proper syntax. The system checks compatibility at runtime in this case.

Caution: If the type of the new reference variable does not match the exact type of the referenced data object, a runtime error occurs. Class CX_SY_MOVE_CAST_ERROR is an exception.

Dereferenced Generically Typed Data References

Figure 195: Dereferencing Generically Typed Data References

The only ABAP statement in which you can dereference a generic reference variable is the ASSIGN statement. The ASSIGN statement assigns a (generic) field symbol to the data object to which the generic reference variable points. You then address and further process the contents of the referenced object using this field symbol.

502

© Copyright . All rights reserved.

Lesson: Using Generic Data Types

LESSON SUMMARY You should now be able to: ●

Explain generic data types of ABAP



Use generic data types



Access data objects dynamically



Use generically typed data references

© Copyright . All rights reserved.

503

Unit 11 Lesson 2 Describing Data Types, Data Objects, and Objects at Runtime

LESSON OVERVIEW This lesson discusses runtime type identification (RTTI), a technique that you use to query information about data types and object types at runtime. This technique is essential to use the generically typed parameters, field symbols, and references in dynamic programs. Business Example You need to develop a flexible application using generically typed parameters, field symbols, and references. You therefore want to learn about the options provided by RTTI for querying information about the actual type of the underlying object at runtime. For this reason, you require the following knowledge: ●

An understanding of how to query the properties of data objects and data types at runtime



An understanding of how to query the properties of classes and instances at runtime

LESSON OBJECTIVES After completing this lesson, you will be able to:

504



Explain the principle of RTTI



Describe data types and data objects at runtime



Describe object types and objects at runtime

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

RTTI Class Hierarchy

Figure 196: Class Hierarchy of RTTI Description Classes  

As of SAP Web AS 6.10, ABAP developers use a class-based concept, RTTI, to determine type properties, such as data types and object types, at runtime. Hint: Before RTTI, ABAP  contained only the DESCRIBE FIELD and DESCRIBE TABLE statements. However, these statements are limited to properties of data objects, and do not determine as many properties as RTTI. RTTI consists of a hierarchy of ten global classes that developers use. The description of a type at runtime is an instance of one of these global classes. The instance attributes save the properties of the type. You query them directly or by using appropriate methods. At runtime, only one description object exists for each type. All classes inherit properties from a shared superclass, either directly or indirectly, and their names all follow the pattern CL_ABAP_xxxDESCR, where xxx stands for the category of the type used to describe the respective class. You need different classes because the attributes and methods of each class specialize to describe a specific category of types. For example, you use class CL_ABAP_TABLEDESCR to describe table types. Therefore, the class contains attributes for the table category and the structure of the table key, among other information. These attributes are specific to class CL_ABAP_TABLEDESCR. No other RTTI classes contain them. RTTI Classes – Purpose

© Copyright . All rights reserved.

505

Unit 11: Dynamic Programming

You can instantiate only six of the ten RTTI classes and use them to describe specific types. The following table lists the RTTI classes that you can instantiate with their purposes: RTTI Class

Purpose

CL_ABAP_ELEMDESCR

To describe elementary data types

CL_ABAP_REFDESCR

To describe reference types (= types of reference variables)

CL_ABAP_STRUCTDESCR

To describe structure types

CL_ABAP_TABLEDESCR

To describe table types

CL_ABAP_CLASSDESCR

To describe classes (= object types)

CL_ABAP_INTFESCR

To describe interfaces

All other classes are abstract, which means that you cannot instantiate them. Use those classes to define the attributes and methods that are used in several of the other classes and implement them if necessary. For example, the METHODS attribute, which contains a list of the methods, is not defined in class CL_ABAP_CLASSDESCR, but instead in class CL_ABAP_OBJECTDESCR, because it is also needed in the same form in class CL_ABAP_INTFDESCR.

Figure 197: RTTI classes you can instantiate

506

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

RTTI Class Instantiation

Figure 198: RTTI – Methods and Attributes of the Root Class

Do not instantiate the RTTI description classes directly with the CREATE OBJECT statement. To retrieve a reference to a description object, call static method DESCRIBE_BY_xxx of class CL_ABAP_TYPEDESCR. The description objects are generated and the data is filled and returned using a return parameter with generic type REF TO CL_ABAP_TYPEDESCR.

© Copyright . All rights reserved.

507

Unit 11: Dynamic Programming

Describe a Type Based on Its Name

Figure 199: Describing a Type Based on Its Name

After the call, you need to cast a suitable subclass to access specific attributes and methods for the respective type. If you do not know which RTTI class was instantiated, evaluate the public KIND instance attribute whose contents match the value of one of the six constants from class CL_ABAP_TYPEDESCR. Each of these six constants corresponds to one of the six RTTI classes that the developer can instantiate.

508

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

Suitable Reference for a Type Description Object

Figure 200: Casing a Suitable Reference for a Type Description Object

Hint: If you know which description class is instantiated, then the down cast can also take place directly in the call of the functional method, for example, lo_class?= cl_abap_typedescr=>describe_by_... In this case, you can catch runtime error CX_SY_MOVE_CAST_ERROR. Methods for Description Objects The following methods differ with regard to the information they are given in their calls: DESCRIBE_BY_NAME



This method returns the description object with the type name that you specify and analyzes both data types and object types (classes and interfaces) that are defined globally in the ABAP Dictionary or Class Builder, or locally in the program. You must enter the type name in upper case. If the method does not find the type with the specified name, it raises a conventional exception TYPE_NOT_FOUND. ●

DESCRIBE_BY_DATA This method returns the description object for the type of a data object. It only returns descriptions of data types, and it does not consider whether the data object was defined with an explicit type or a bound type.

© Copyright . All rights reserved.

509

Unit 11: Dynamic Programming

If the specified data object is a parameter or field symbol with a generic type, the method does not return the description of the generic type. Instead, it returns the type of the currently assigned actual parameter or data object. ●

DESCRIBE_BY_DATA_REF This method returns the description object for the type of a data object that points to a data reference. It only returns descriptions of data types. If the data reference is typed generically (TYPE REF TO DATA), you can use this method to determine the dynamic type of the referenced object.

Caution: If the reference does not have a valid value at call time, the method raises conventional exception REFERENCE_IS_INITIAL.   ●

DESCRIBE_BY_OBJECT_REF This method returns the description object for the type of an instance that points to an object reference. It only returns descriptions of classes. Use this method to determine the dynamic type of the referenced instance after an up cast to a superclass or implemented interface.

Caution: If the reference does not have a valid value at call time, the method raises conventional exception REFERENCE_IS_INITIAL.

510

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

Describe Types Based on Data Objects and References

Figure 201: Describing Types Based on Data Objects and References

The figure shows examples to use these static methods. In addition to static methods, you use special methods to navigate from one description object to other description objects. For example, you want to navigate from the description of a table type to the description of the corresponding line type, or you want to navigate from a structure type to the description objects for the component types.

© Copyright . All rights reserved.

511

Unit 11: Dynamic Programming

Elementary Data Type Analysis

Figure 202: Analysis of an Elementary Data Type

The application examples demonstrate how to use RTTI to determine the properties of different data types. Whether the system uses a given subclass depends on the data type. An instance of class CL_ABAP_ELEMDESCR describes all the properties of an elementary data type. The corresponding public attributes contain the technical properties of the underlying ABAP type, the length, and the number of decimal places. To evaluate the TYPE_KIND attribute, compare its contents with the corresponding constants from class CL_ABAP_TYPEDESCR, as you must do to evaluate the KIND attribute.

Note: The three attributes are described in the root class of RTTI, which means they are inherited by all description classes. However, in the other classes, these attributes are less significant. The semantic properties, that is, the additional information from the ABAP Dictionary, must be determined explicitly using public methods. The figure shows a call of method GET_DDIC_FIELD. You use an optional parameter to determine language-dependent information, such as field labels, in a language other than the current logon language.

512

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

Caution: If the current type is not a dictionary type, the method raises a conventional exception. To avoid this, use method IS_DDIC_TYPE to check whether dictionary information is available (see the example given in the figure).

Reference Type Analysis

Figure 203: Analysis of the Type of a Reference Variable

When you analyze a reference type (= type of a reference variable), the inherited TYPE_KIND attribute allows you to differentiate between object references and data references. However, to determine the details of the static type of the reference variable, use the GET_REFERENCED_TYPE navigation method. This method returns a reference to another description object. This description object can be an instance of class CL_ABAP_STRUCTDESCR if the reference variable was created with a structure type. However, if you create the reference variable with reference to a class or an interface, then GET_REFERENCED_TYPE returns instances of the CL_ABAP_CLASSDESCR or CL_ABAP_INTFDESCR class, respectively.

© Copyright . All rights reserved.

513

Unit 11: Dynamic Programming

Structure Type Analysis

Figure 204: Navigation from Structure Type to Component Types

To gain full access to all properties of the component types, navigate to the respective description objects. The GET_COMPONENT_TYPE navigation method returns the description object for the type of a specific component, while the GET_COMPONENTS navigation method returns the description objects for all components.

Hint: Because component types are also reference types, structure types, or table types, define the return values with type REF TO CL_ABAP_DATADESCR. A down cast to one of the subclasses may be necessary in reference variables, for example, to type REF TO CL_ABAP_ELEMDESCR.

514

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

Table Type Analysis

Figure 205: Analysis of a Table Type

The public attributes of class CL_ABAP_TABLEDESCR include the table types such as standard, sorted, hashed, index, any, uniqueness of the key, and a list of names of the key components. To determine the details for a line type, navigate to a description object for that line type the GET_TABLE_LINE_TYPE navigation method. Hint: The line type of a table type can have any data type. Accordingly, the return parameter is typed with REF TO CL_ABAP_DATADESCR and performs a down cast to a suitable type if necessary.

© Copyright . All rights reserved.

515

Unit 11: Dynamic Programming

516

© Copyright . All rights reserved.

Unit 11 Exercise 28 Provide Column Headers Using Runtime Type Identification

Business Example You need to develop a simple program that displays the contents of any database table. To develop the program, you need to find out about the options available in dynamic programming. You have already developed a method to output any internal table with a flat line type to a list. You need to use the options of RTTI to develop a method that generates dynamic column headers for the program. Use RTTI to analyze a structure type and to determine semantic information for that structure type from the ABAP Dictionary. Use the semantic information for the structure type to generate column headers dynamically. Task 1 Copy template CL_BC402_DYT_RTTI_HEADERS and name it ZCL_BC402_##_RTTI_HEADERS, where ## is your group number. Familiarize yourself with the class signature. 1. Copy the global class. 2. Analyze the class signature. Determine which methods are defined and what their purposes are? 3. Which parameters and exceptions do these methods have? How are the parameters typed? Which error situations correspond to the exceptions?

Task 2 Implement method write_headers. Use RTTI options to analyze the type of which the name is contained in import parameter gv_tabname. 1. Call a suitable static method of class CL_ABAP_TYPEDESCR to analyze the data type based on its name. 2. Create a local reference variable (suggested name is lo_type) and enter it to match the return parameter of the method. Specify this reference variable as an actual parameter in the method call. 3. Handle any possible exceptions and raise exception TYPE_NOT_FOUND from method write_headers as a reaction.

© Copyright . All rights reserved.

517

Unit 11: Dynamic Programming

4. Use the public KIND attribute to determine whether the generated RTTI instance actually describes a structure type. If the data type is not a structure type, exit method write_headers with exception NO_STRUCTURE. 5. Create a local reference variable (suggested name is lo_struct) and assign it to a type so that it points to instances of class CL_ABAP_STRUCTDESCR. Program a down cast to point this reference to the type description object. Hint: Do not catch possible runtime errors here because the query of the KIND attribute already ensures compatibility.

Task 3 Determine a list with dictionary information for all components of the structure type. Output the report header for all components in sequence. Ensure that the output does not exceed the display length of the corresponding field. 1. Create an internal table with type ddfields (suggested name: lt_fields). 2. Call a suitable method of class CL_ABAP_STRUCTDESCR to generate a list with dictionary information for the structure components. To do so, create an internal table with type ddfields as the actual parameter for the return value (suggested name is lt_fields). If the method call terminates with exceptions, exit the write_headers method with a suitable exception. 3. To program a loop over the internal table, create a field symbol (suggested name is ) that is typed with the line type of internal table lt_fields. 4. Output the report header (field reptext) in each loop pass. Use the output length (field outputlen) for length access to ensure the headers are exactly as long as they will be output later.

Task 4 Copy program BC402_DYS_GEN_TYPES or your own program, ZBC402_##_GEN_TYPES and name it ZBC402_##_RTTI_HEADERS, where ## is your group number. Familiarize yourself with the program and how it works. 1. Copy the program and all its subcomponents. 2. Activate and test the program. Analyze the source code.

Task 5 Insert a call of method write_headers before the data output. Pass the name of the line type of the internal table with the data to your method.

518

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

1. Implement a call of method write_headers before the call of method write_any_table. Pass the data object that contains the name of the database table (and therefore the name  of the line type of the internal table). 2. React to exceptions with suitable error messages from message class BC402. 3. Activate and test the program.

© Copyright . All rights reserved.

519

Unit 11 Solution 28 Provide Column Headers Using Runtime Type Identification

Business Example You need to develop a simple program that displays the contents of any database table. To develop the program, you need to find out about the options available in dynamic programming. You have already developed a method to output any internal table with a flat line type to a list. You need to use the options of RTTI to develop a method that generates dynamic column headers for the program. Use RTTI to analyze a structure type and to determine semantic information for that structure type from the ABAP Dictionary. Use the semantic information for the structure type to generate column headers dynamically. Task 1 Copy template CL_BC402_DYT_RTTI_HEADERS and name it ZCL_BC402_##_RTTI_HEADERS, where ## is your group number. Familiarize yourself with the class signature. 1. Copy the global class. a) Perform this step as usual. 2. Analyze the class signature. Determine which methods are defined and what their purposes are? a) write_headers to output a list of column headers based on a structure type from the ABAP Dictionary. 3. Which parameters and exceptions do these methods have? How are the parameters typed? Which error situations correspond to the exceptions? a) Parameter iv_tabname with generic type csequence and exceptions. Error situations that correspond to the exceptions are as follows: ●

TYPE_NOT_FOUND The passed on type is unknown.



NO_STRUCTURE The object is not a structure type.



NO_DDIC_TYPE The object is not a type in the ABAP Dictionary.

520

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

Task 2 Implement method write_headers. Use RTTI options to analyze the type of which the name is contained in import parameter gv_tabname. 1. Call a suitable static method of class CL_ABAP_TYPEDESCR to analyze the data type based on its name. a) See the source code excerpt from the model solution. 2. Create a local reference variable (suggested name is lo_type) and enter it to match the return parameter of the method. Specify this reference variable as an actual parameter in the method call. a) See the source code excerpt from the model solution. 3. Handle any possible exceptions and raise exception TYPE_NOT_FOUND from method write_headers as a reaction. 4. Use the public KIND attribute to determine whether the generated RTTI instance actually describes a structure type. If the data type is not a structure type, exit method write_headers with exception NO_STRUCTURE. a) See the source code excerpt from the model solution. 5. Create a local reference variable (suggested name is lo_struct) and assign it to a type so that it points to instances of class CL_ABAP_STRUCTDESCR. Program a down cast to point this reference to the type description object. Hint: Do not catch possible runtime errors here because the query of the KIND attribute already ensures compatibility. a) See the source code excerpt from the model solution.

Task 3 Determine a list with dictionary information for all components of the structure type. Output the report header for all components in sequence. Ensure that the output does not exceed the display length of the corresponding field. 1. Create an internal table with type ddfields (suggested name: lt_fields). a) See the source code excerpt from the model solution. 2. Call a suitable method of class CL_ABAP_STRUCTDESCR to generate a list with dictionary information for the structure components. To do so, create an internal table with type ddfields as the actual parameter for the return value (suggested name is lt_fields). If the method call terminates with exceptions, exit the write_headers method with a suitable exception. a) See the source code excerpt from the model solution.

© Copyright . All rights reserved.

521

Unit 11: Dynamic Programming

3. To program a loop over the internal table, create a field symbol (suggested name is ) that is typed with the line type of internal table lt_fields. a) See the source code excerpt from the model solution. 4. Output the report header (field reptext) in each loop pass. Use the output length (field outputlen) for length access to ensure the headers are exactly as long as they will be output later. a) See the source code excerpt from the model solution.

Task 4 Copy program BC402_DYS_GEN_TYPES or your own program, ZBC402_##_GEN_TYPES and name it ZBC402_##_RTTI_HEADERS, where ## is your group number. Familiarize yourself with the program and how it works. 1. Copy the program and all its subcomponents. a) Perform this step in the usual way. 2. Activate and test the program. Analyze the source code. a) Perform this step in the usual way.

Task 5 Insert a call of method write_headers before the data output. Pass the name of the line type of the internal table with the data to your method. 1. Implement a call of method write_headers before the call of method write_any_table. Pass the data object that contains the name of the database table (and therefore the name  of the line type of the internal table). a) See the source code excerpt from the model solution. 2. React to exceptions with suitable error messages from message class BC402. a) See the source code excerpt from the model solution. 3. Activate and test the program. a) Perform this step as usual. Method write_headers (Class_CL_BC402_DYS_RTTI_HEADERS) METHOD write_headers. DATA: lo_type TYPE REF TO cl_abap_typedescr, lo_struct TYPE REF TO cl_abap_structdescr, lt_flist TYPE ddfields. FIELD-SYMBOLS: LIKE LINE OF lt_flist.

522

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

CALL METHOD cl_abap_typedescr=>describe_by_name EXPORTING p_name = iv_tabname RECEIVING p_descr_ref = lo_type EXCEPTIONS type_not_found = 1. IF sy-subrc 0. RAISE type_not_found. ENDIF. IF lo_type->kind cl_abap_typedescr=>kind_struct. RAISE no_structure. ENDIF. lo_struct ?= lo_type. CALL METHOD lo_struct->get_ddic_field_list RECEIVING p_field_list = lt_flist EXCEPTIONS not_found = 1 no_ddic_type = 2. CASE sy-subrc. WHEN 1. RAISE type_not_found. WHEN 2. RAISE no_ddic_type. ENDCASE. NEW-LINE. LOOP AT lt_flist ASSIGNING . WRITE -reptext(-outputlen) COLOR COL_HEADING. ENDLOOP. ULINE. ENDMETHOD. Executable Program BC402_DYS_RTTI_HEADERS REPORT

bc402_dys_rtti_headers MESSAGE-ID bc402.

TYPE-POOLS: abap. DATA: gt_cust gt_conn

TYPE ty_customers, TYPE ty_connections.

DATA: gv_tabname

TYPE string.

FIELD-SYMBOLS:

© Copyright . All rights reserved.

523

Unit 11: Dynamic Programming

TYPE ANY TABLE. SELECTION-SCREEN COMMENT 1(80) text-sel. PARAMETERS: pa_xconn TYPE xfeld RADIOBUTTON GROUP tab DEFAULT 'X', pa_xcust TYPE xfeld RADIOBUTTON GROUP tab . PARAMETERS: pa_nol TYPE i DEFAULT '100'. START-OF-SELECTION. * specific part *----------------------------------------------------* CASE 'X'. WHEN pa_xconn. gv_tabname = 'SPFLI'. ASSIGN gt_conn TO . WHEN pa_xcust. gv_tabname = 'SCUSTOM'. ASSIGN gt_cust TO . ENDCASE. * dynamic part *------------------------------------------------------* TRY.

SELECT * FROM (gv_tabname) INTO TABLE UP TO pa_nol ROWS. CATCH cx_sy_dynamic_osql_error. MESSAGE e061. ENDTRY. CALL METHOD cl_bc402_dys_rtti_headers=>write_headers EXPORTING iv_tabname = gv_tabname EXCEPTIONS type_not_found = 1 no_structure = 2 no_ddic_type = 3. CASE sy-subrc. WHEN 1. MESSAGE e050 WITH gv_tabname. WHEN 2. MESSAGE e051 WITH gv_tabname. WHEN 3. MESSAGE e052 WITH gv_tabname. ENDCASE. cl_bc402_dys_gen_types=>write_any_table( ).

524

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

Object Type Analysis

Figure 206: Analysis of an Object Type

RTTI permits you to analyze the attributes of objects. Perform analysis by using classes CL_ABAP_CLASSDESCR and CL_ABAP_INTFDESCR. Most of the attributes and methods for these two classes are defined in the (abstract) shared superclass CL_ABAP_OBJECTDESCR because they are required to analyze classes and interfaces.

Note: A class is analyzed in the example shown in the figure. Most of the information also applies to the analysis of interfaces. Class CL_ABAP_CLASSDESCR contains public attributes that list the attributes, methods, events, interfaces, and other objects of the described class. Internal tables in the system contain these public attributes. Some of these attributes, such as METHODS, are defined as nested internal tables in which each line itself contains one or more internal tables. For example, these nested internal tables contain lists with parameters and exceptions for the respective method. In addition to these inherited attributes, class CL_ABAP_CLASSDESCR also provides specific attributes, such as the CLASS_KIND attribute, which you use to determine whether the class was flagged as abstract, final, and so on.

© Copyright . All rights reserved.

525

Unit 11: Dynamic Programming

Note: Class CL_ABAP_INTFDESCR contains an INTF_KIND attribute instead, which you use to determine whether an interface is comprised of multiple interfaces. The figure demonstrates how to use RTTI to determine all the parameters of the constructor for class CL_RENTAL. After the system generates the description object and performs the down cast, it reads the description of the constructor method from the list of methods (statement with READ TABLE). The system then evaluates the list of parameters for the constructor method in a loop (LOOP over the inner internal table). The description classes for object types also provide navigation methods for determining the details of a used type. For example, the GET_ATTRIBUTE_TYPE method returns the description object for the type of a specific attribute, while GET_METHOD_PARAMETER_TYPE analyzes the type of a specific method parameter, and so on. The GET_SUPER_CLASS_TYPE method is specific to classes. It returns the description object for the direct superclass, if any.

526

© Copyright . All rights reserved.

Lesson: Describing Data Types, Data Objects, and Objects at Runtime

LESSON SUMMARY You should now be able to: ●

Explain the principle of RTTI



Describe data types and data objects at runtime



Describe object types and objects at runtime

© Copyright . All rights reserved.

527

Unit 11 Lesson 3 Creating Data Types, Data Objects, and Objects at Runtime

LESSON OVERVIEW This lesson discusses the method for generating objects, that is, instances of classes, at runtime from object-oriented programming. It discusses a similar method for generating data objects as instances of data types at runtime. The lesson also discusses runtime type creation (RTTC), a technique that enables you to define the data type at runtime. Business Example You need to develop a flexible application. In addition to accessing existing data objects dynamically and analyzing the underlying data types, you also want to learn about the techniques available to generate objects, data objects, and data types at runtime according to the requirements of program. For this reason, you require the following knowledge: ●

An understanding of how to generate objects or instances at runtime



An understanding of how to generate data objects at runtime



An understanding of how to generate data types at runtime

LESSON OBJECTIVES After completing this lesson, you will be able to:

528



Create objects (instances) at runtime



Create data objects at runtime



Create data types at runtime

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

Dynamic Object Creation

Figure 207: Options for Generating Objects at Runtime

The CREATE OBJECT statement generates objects or specifically, instances of classes at runtime. Define the type of object, that is, the class to be instantiated implicitly through the static type of the reference variable used. Alternatively, use the TYPE addition to specify the class to be instantiated in the CREATE OBJECT statement. Apply the following rules while using the CREATE OBJECT statement: A class, not an interface, must appear after the TYPE addition.





You must be able to instantiate the class, which means that it cannot be flagged as abstract.



The static type of the reference variable must be compatible with the class.

The last rule applies because the system carries out an implicit up cast if necessary when you specify the type explicitly. The reference variable can become an object if it meets one of the following conditions: ● The reference variable is typed with the class to be instantiated. ●





The reference variable is typed with a superclass of the class to be instantiated. The reference variable is typed with an interface that is implemented by the class to be instantiated. The reference variable is typed with generic type REF TO OBJECT type.

The syntax for specifying an explicit type can include a data object in parentheses after TYPE. This syntax enables dynamic selection of the class to be instantiated.

© Copyright . All rights reserved.

529

Unit 11: Dynamic Programming

Hint: If classes are available for selections that are not linked through a shared superclass or the same implementing interface, type the reference variable completely generically with TYPE REF TO OBJECT.

Dynamic Passing of Parameters

Figure 208: Dynamic Passing of Parameters

If all potential classes have the same constructor signature, provide the parameters with data statically. However, it is likely that the parameters and exceptions of the constructors will differ. In this case, you need to use dynamic parameter transfer. Like with dynamic method calls, perform dynamic parameter transfer using internal tables after the PARAMETER-TABLE and EXCEPTION-TABLE additions. Enter these tables and fill them as you do for method calls.

530

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

Dynamic Data Object Creation

Figure 209: Options for Creating Data Objects at Runtime

You can also create data objects at runtime. The corresponding statement, CREATE DATA, has a similar definition to that of the CREATE OBJECT statement. The CREATE DATA statement creates a data object dynamically, assigns memory to it, and points the general data reference variable to that data object in memory. The data object is not given a name, so it is often called an anonymous data object. To address the data object, dereference the reference variable at runtime.

Hint: In contrast to the static DATA declaration, the system does not reserve the memory for the data objects until runtime, and it does not reserve the memory when the respective program is loaded. Like with class instances, the garbage collector releases the memory again as soon as the program deletes the last reference to the data object. Use CREATE DATA to define the type of the data object implicitly by using the type of the reference variable, or explicitly by using the TYPE addition. To use a number of variants that you are familiar with, use explicit typing. These variants can be from DATA declarations, such as the use of built-in types, the implicit construction of table types, and the reference to an existing data object with LIKE. To define the data type for the generated data objects dynamically, use character-type data objects in parentheses.

© Copyright . All rights reserved.

531

Unit 11: Dynamic Programming

Note: Alternatively, use the TYPE HANDLE addition to refer to a type description object from the RTTI.

Access to Dynamically Created Data Objects

Figure 210: Access to Dynamically Created Data Objects

If the system determines the data type dynamically, type the reference variable generically with TYPE REF TO DATA. This is the only generic type that supports data references at present. You assign a field symbol to the references data object for the following reasons: ●

You can only dereference the generic data reference in the ASSIGN statement.



You can use generically typed field symbols anywhere.

Hint: If the new data object is an internal table and you want to use it in the corresponding operand positions, the field symbol must contain at least type ANY TABLE.

532

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

Dynamically Generated Internal Table and Dynamic SELECT

Figure 211: Example – Dynamically Generated Internal Table and Dynamic SELECT

The figure shows an example of a dynamic database access in which the suitable data object is generated at runtime.

© Copyright . All rights reserved.

533

Unit 11: Dynamic Programming

534

© Copyright . All rights reserved.

Unit 11 Exercise 29 Create Data Objects at Runtime

Business Example You need to develop a simple program that displays the contents of any database table by using the options available in dynamic programming. Generate and use data objects at runtime, and use generically typed reference variables. Task 1 Copy program BC402_DYS_RTTI_HEADERS or your own program, ZBC402_##_RTTI_HEADERS and name it ZBC402_##_CREATE_DATA, where ## is your group number. Familiarize yourself with the program and how it works.

Hint: If you have not performed the exercise on RTTI, simply copy program ZBC402_##_GEN_DATA. The display of the column headers is not relevant to this exercise. 1. Copy the program and all its subcomponents. 2. Activate and test the program. Analyze the source code. Which data objects are filled  during the database access? Which types do they have? Were they created statically or dynamically?

Task 2 Replace the two statically defined internal tables with a data object that you generate after the CASE structure (standard table with non-unique standard key). Define the type of the data object dynamically to ensure that the line type precisely matches the structure of the database table you want to read. 1. Define a generically typed data reference (suggested name is gr_data). 2. Use the gr_data data reference to generate an internal table immediately after the ENDCASE statement. Access the contents of data object gv_tabname to define the line type of the table dynamically. 3. Move one of the ASSIGN statements outside the WHEN blocks after the data object is generated, and delete the other ASSIGN statement. Replace the statically defined internal table with the dynamically generated table.

© Copyright . All rights reserved.

535

Unit 11: Dynamic Programming

Hint: Dereference the generic data reference.

4. Why can you not continue to use gr_data directly? 5. Delete the definitions of the two static internal tables or flag them as comments. 6. Activate and test your program.

Task 3 The static part of the program now contains only the filling of data object gv_tabname with an appropriate literal for the name of the database table. Replace both checkboxes on the selection screen with a parameter for the name of any database table. 1. Delete the definitions parameters of the two checkboxes or flag them as comments. Copy the user entry from the parameter directly to data object gv_tabname instead of evaluating the checkboxes in a CASE structure. 2. Create a new parameter (suggested name is pa_tab). Hint: If you use the global type dd02l-tabname, provide a value (F4) help function for the users. 3. Delete the CASE structure or flag it as comments. In the same position, program a value assignment from pa_tab to gv_tabname. 4. Activate and test your program.

536

© Copyright . All rights reserved.

Unit 11 Solution 29 Create Data Objects at Runtime

Business Example You need to develop a simple program that displays the contents of any database table by using the options available in dynamic programming. Generate and use data objects at runtime, and use generically typed reference variables. Task 1 Copy program BC402_DYS_RTTI_HEADERS or your own program, ZBC402_##_RTTI_HEADERS and name it ZBC402_##_CREATE_DATA, where ## is your group number. Familiarize yourself with the program and how it works.

Hint: If you have not performed the exercise on RTTI, simply copy program ZBC402_##_GEN_DATA. The display of the column headers is not relevant to this exercise. 1. Copy the program and all its subcomponents. a) Perform this step as usual. 2. Activate and test the program. Analyze the source code. Which data objects are filled  during the database access? Which types do they have? Were they created statically or dynamically? a) One of two internal tables, gt_conn or gt_cust, is filled depending on the user entry. While the data object assigned to field symbol (which is therefore addressed in the SELECT statement) is determined dynamically, the data objects themselves have static definitions (DATA statement).

Task 2 Replace the two statically defined internal tables with a data object that you generate after the CASE structure (standard table with non-unique standard key). Define the type of the data object dynamically to ensure that the line type precisely matches the structure of the database table you want to read. 1. Define a generically typed data reference (suggested name is gr_data). a) See the source code excerpt from the model solution.

© Copyright . All rights reserved.

537

Unit 11: Dynamic Programming

2. Use the gr_data data reference to generate an internal table immediately after the ENDCASE statement. Access the contents of data object gv_tabname to define the line type of the table dynamically. a) See the source code excerpt from the model solution. 3. Move one of the ASSIGN statements outside the WHEN blocks after the data object is generated, and delete the other ASSIGN statement. Replace the statically defined internal table with the dynamically generated table. Hint: Dereference the generic data reference.

a) See the source code excerpt from the model solution. 4. Why can you not continue to use gr_data directly? a) Because gr_data has a generic type and ABAP only allows dereferenced access to generically typed data references in ASSIGN statements. 5. Delete the definitions of the two static internal tables or flag them as comments. a) See the source code excerpt from the model solution. 6. Activate and test your program. a) Perform this step as usual.

Task 3 The static part of the program now contains only the filling of data object gv_tabname with an appropriate literal for the name of the database table. Replace both checkboxes on the selection screen with a parameter for the name of any database table. 1. Delete the definitions parameters of the two checkboxes or flag them as comments. Copy the user entry from the parameter directly to data object gv_tabname instead of evaluating the checkboxes in a CASE structure. a) See the source code excerpt from the model solution. 2. Create a new parameter (suggested name is pa_tab). Hint: If you use the global type dd02l-tabname, provide a value (F4) help function for the users. a) See the source code excerpt from the model solution. 3. Delete the CASE structure or flag it as comments. In the same position, program a value assignment from pa_tab to gv_tabname. a) See the source code excerpt from the model solution.

538

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

4. Activate and test your program. a) Perform this step as usual. *&--------------------------------------* *& Report BC402_DYS_CREATE_DATA *& *&--------------------------------------* *& *& *&--------------------------------------* REPORT bc402_dys_create_data MESSAGE-ID bc402. *DATA: * gt_cust TYPE ty_customers, * gt_conn TYPE ty_connections. DATA: gr_data TYPE REF TO data. DATA: gv_tabname TYPE string. FIELD-SYMBOLS: TYPE ANY TABLE. SELECTION-SCREEN COMMENT 1(80) text-sel. *PARAMETERS: * pa_xconn TYPE xfeld RADIOBUTTON GROUP tab DEFAULT 'X', * pa_xcust TYPE xfeld RADIOBUTTON GROUP tab . PARAMETERS pa_tab TYPE dd02l-tabname DEFAULT 'SPFLI'. PARAMETERS: pa_nol TYPE i DEFAULT '100'. START-OF-SELECTION. * specific part *---------------------------------* * CASE 'X'. * WHEN pa_xconn. * * gv_tabname = 'SPFLI'. * ASSIGN gt_conn TO . * * WHEN pa_xcust. * * gv_tabname = 'SCUSTOM'. * ASSIGN gt_cust TO . * * ENDCASE. * dynamic part *---------------------------------* gv_tabname = pa_tab. CREATE DATA gr_data TYPE TABLE OF (gv_tabname). ASSIGN gr_data->* TO . TRY.

© Copyright . All rights reserved.

539

Unit 11: Dynamic Programming

SELECT * FROM (gv_tabname) INTO TABLE UP TO pa_nol ROWS. CATCH cx_sy_dynamic_osql_error. MESSAGE e061. ENDTRY. CALL METHOD cl_bc402_dys_rtti_headers=>write_headers EXPORTING iv_tabname = gv_tabname EXCEPTIONS type_not_found = 1 no_structure = 2 no_ddic_type = 3. CASE sy-subrc. WHEN 1. MESSAGE e050 WITH gv_tabname. WHEN 2. MESSAGE e051 WITH gv_tabname. WHEN 3. MESSAGE e052 WITH gv_tabname. ENDCASE. cl_bc402_dys_gen_types=>write_any_table( ).

540

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

Runtime Type Creation (RTTC)

Figure 212: Dynamic Type Creation Methods of Runtime Type Services

RTTI enables you to describe data types and object types with instances of RTTI classes or type description objects. The RTTI concept was enhanced in SAP Web AS 6.40. In addition to describing existing types, you use it to generate new types. This enhanced function set is called runtime type creation (RTTC). RTTC consists of a number of additional static methods in the RTTI description classes.

Hint: Note that type generation is restricted to data types. You cannot generate classes or interfaces dynamically. In the figure, the CL_ABAP_REFDESCR, CL_ABAP_STRUCTDESCR, and CL_ABAP_TABLEDESCR classes are enhanced with a CREATE method, while the CL_ABAP_ELEMDESCR class receives an appropriate GET method for each built-in elementary ABAP type such as, GET_I, GET_F, GET_C, GET_STRING. These methods return pointers to an instance of the respective class. In contrast to the DESCRIBE methods of the root class, the attribute values of this instance do not come from analyzing a data object, a reference, or a named type. Instead, they are passed on to the RTTC method explicitly. The method signatures have been designed accordingly. While the GET_I method does not need any other input (type i is complete), method GET_P has two import parameters defined: one for length and the other for the number of decimal places.

© Copyright . All rights reserved.

541

Unit 11: Dynamic Programming

The CREATE method for reference types expects the pointer to the description object for the referenced type, while the CREATE method for structure types expects a list with names and types of the components. When table types are generated, a reference to an RTTI object that describes the line type is expected (among other things).

Dynamic Table Type Creation

Figure 213: RTTC – Creating a Table Type

The figure shows how to generate a table type dynamically with RTTC. You are required to specify only the P_LINE_TYPE parameter for the CREATE method. The parameter is of type REF TO CL_ABAP_DATADESCR and needs to be supplied with a reference to any description object for a data type.  In the example shown in the figure, SPFLI is used as the line type. The DESCRIBE_BY_NAME method returns the matching description object. The optional parameters are used to define the table type and key. If you do not specify them, the system uses a standard table with a non-unique standard key.

542

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

Usage of a Dynamically Created Data Type

Figure 214: Generating an Internal Table with a Dynamically Created Type

To dynamically create a data object with this specific type, use the dynamically generated type in the CREATE DATA statement. Use the HANDLE addition with the CREATE DATA statement to generate a data object whose type matches the specified type description object. Specify the HANDLE as a reference variable with static type CL_ABAP_DATADESCR or one of its subclasses. The system may have created the object based on the existing data types by using RTTI methods or by dynamically defining a new data type.

© Copyright . All rights reserved.

543

Unit 11: Dynamic Programming

544

© Copyright . All rights reserved.

Unit 11 Exercise 30 Create Data Types at Runtime with Runtime Type Creation (RTTC)

Business Example You have developed a simple program that displays the contents of any database table. The program now needs to allow users to select the specific columns they want to read and display. You need to use function module BC402_SELECT_COMPONENTS, which displays all the components of a global structure type and enables users to select components. Therefore, you need to use the options of runtime type creation (RTTC) to generate a table type dynamically. The table type should only contain the user-selected components in its lines. Use RTTC to generate structure types and table types at runtime, and generate data objects based on dynamic data types. Task 1 Display function module BC402_SELECT_COMPONENTS. Analyze the interface and test the functional scope of the function module. 1. Display the function module. Analyze the interface. Which parameters are there and what  are their types? 2. Which exceptions can the function module raise, and what purpose do they serve? 3. Test the function module.

Task 2 Copy program BC402_DYS_CREATE_DATA or your own program ZBC402_##_CREATE_DATA and name it ZBC402_##_RTTC, where ## is your group number. Familiarize yourself with the program and how it works. Implement a call of the function module before the dynamic generation of the data object. Pass the table name that the user entered on the selection screen to the import parameter. 1. Copy the program and all its subcomponents. 2. Call the function module before the CREATE DATA statement. Create a suitably typed data object to supply the export parameter with data. Pass the contents of gv_tabname to the import parameter. React to exceptions with suitable error messages from message class BC402.

© Copyright . All rights reserved.

545

Unit 11: Dynamic Programming

Task 3 Copy template CL_BC402_DYT_RTTC and name it ZCL_BC402_##_RTTC, where ## is your group number. Familiarize yourself with the signature of method create_table_type. 1. Copy the global class. 2. Analyze the create_table_type method signature. Which parameters are defined? How are they typed?

Task 4 Implement the create_table_type method. Use the RTTI techniques to analyze the data type of which the name is contained in the import parameter. Use a suitable navigation method to calculate a list with the names and RTTI type description objects for all components in the structure. 1. Call a suitable method of class CL_ABAP_TYPEDESCR to generate a type description object for the data type. Create a reference variable with a suitable type for the return value (suggested name: lo_struct). Hint: For simplicity, assume that the data type is a structure type in the ABAP Dictionary and perform a direct down cast to the corresponding reference variable. 2. Call the get_components method for the RTTI instance. Create a data object with a suitable type for the return value (suggested name is lt_comps).

Task 5 Change the list of components so that it only contains the components listed in import parameter it_comp_names. Based on this list of components, create a new structure type, and then a new table type. 1. Implement a loop over the lt_comps component list. 2. Check whether the component name in each line is contained in import parameter it_comp_names. Hint: Use a statement such as FIND ... IN TABLE or READ TABLE ... TRANSPORTING NO FIELDS. 3. Remove the current line from lt_comps if the corresponding table name is not contained in import parameter it_comp_names.

546

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

Hint: Use the abbreviated syntax for index access in loops here.

4. To generate an RTTI type description object for a new structure type, call the CREATE method of class CL_ABAP_STRUCTDESCR. Pass the reduced component list to the method. Create a data object with a suitable type for the return parameter (suggested name: lo_struct_new). 5. To generate an RTTI type description object for a new table type, call the CREATE method of class CL_ABAP_TABLEDESCR. Pass the reference to the RTTI object for the new structure type. Leave all the optional parameters set to their default values. Transfer the result of the method call directly to return parameter ro_table_def of method create_table_type.

Task 6 Go back to your executable program ZBC402_##_RTTC. Call method create_table_type to generate a table type according to the requirements of the user. Use a new data type when you generate the data object dynamically. Change the SELECT statement so that it reads only those fields from the database that are contained in the line type of the internal table.

Hint: Method write_headers still outputs the headers for all the columns in the table. You either work without the headers completely or use method write_headers_by_data from class CL_BC402_DYS_RTTI_HEADERS. This method analyzes the actual line type of an internal table and outputs the column headers for it. 1. Call method create_table_type in the program directly after the call of function module  BC402_SELECT_COMPONENTS. Pass the name of the database table and the list of components that the user selected to the method create_table_type. 2. Change the type in the CREATE DATA statement. Use the TYPE HANDLE addition to use the newly generated table type. 3. Change the SELECT statement. Use the list of component names as a dynamic field list. Hint: Alternatively, use the INTO CORRESPONDING FIELDS OF TABLE addition.

4. Activate and test your program.

© Copyright . All rights reserved.

547

Unit 11 Solution 30 Create Data Types at Runtime with Runtime Type Creation (RTTC)

Business Example You have developed a simple program that displays the contents of any database table. The program now needs to allow users to select the specific columns they want to read and display. You need to use function module BC402_SELECT_COMPONENTS, which displays all the components of a global structure type and enables users to select components. Therefore, you need to use the options of runtime type creation (RTTC) to generate a table type dynamically. The table type should only contain the user-selected components in its lines. Use RTTC to generate structure types and table types at runtime, and generate data objects based on dynamic data types. Task 1 Display function module BC402_SELECT_COMPONENTS. Analyze the interface and test the functional scope of the function module. 1. Display the function module. Analyze the interface. Which parameters are there and what  are their types? a) There is one import parameter, iv_tabname, with type csequence and one export parameter, et_comp_names, with type string_table (standard table with string line type). 2. Which exceptions can the function module raise, and what purpose do they serve? a) The exceptions raised by the function module and the purposes served by those exceptions are as follows: ●

TYPE_NOT_FOUND The passed on type is unknown.



NO_STRUCTURE The passed on type is not a structure.



NO_DDIC_TYPE The passed on type is not a DDIC type.

3. Test the function module. a) Perform this step as usual.

Task 2

548

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

Copy program BC402_DYS_CREATE_DATA or your own program ZBC402_##_CREATE_DATA and name it ZBC402_##_RTTC, where ## is your group number. Familiarize yourself with the program and how it works. Implement a call of the function module before the dynamic generation of the data object. Pass the table name that the user entered on the selection screen to the import parameter. 1. Copy the program and all its subcomponents. a) Perform this step as usual. 2. Call the function module before the CREATE DATA statement. Create a suitably typed data object to supply the export parameter with data. Pass the contents of gv_tabname to the import parameter. React to exceptions with suitable error messages from message class BC402. a) See the source code excerpt from the model solution.

Task 3 Copy template CL_BC402_DYT_RTTC and name it ZCL_BC402_##_RTTC, where ## is your group number. Familiarize yourself with the signature of method create_table_type. 1. Copy the global class. a) Perform this step as usual. 2. Analyze the create_table_type method signature. Which parameters are defined? How are they typed? a) Import parameter iv_tabname with generic type csequence, import parameter it_comp_names with type string_table, and return parameter ro_tabledescr, a reference to class cl_abap_tabledescr.

Task 4 Implement the create_table_type method. Use the RTTI techniques to analyze the data type of which the name is contained in the import parameter. Use a suitable navigation method to calculate a list with the names and RTTI type description objects for all components in the structure. 1. Call a suitable method of class CL_ABAP_TYPEDESCR to generate a type description object for the data type. Create a reference variable with a suitable type for the return value (suggested name: lo_struct). Hint: For simplicity, assume that the data type is a structure type in the ABAP Dictionary and perform a direct down cast to the corresponding reference variable. a) See the source code excerpt from the model solution.

© Copyright . All rights reserved.

549

Unit 11: Dynamic Programming

2. Call the get_components method for the RTTI instance. Create a data object with a suitable type for the return value (suggested name is lt_comps). a) See the source code excerpt from the model solution.

Task 5 Change the list of components so that it only contains the components listed in import parameter it_comp_names. Based on this list of components, create a new structure type, and then a new table type. 1. Implement a loop over the lt_comps component list. a) See the source code excerpt from the model solution. 2. Check whether the component name in each line is contained in import parameter it_comp_names. Hint: Use a statement such as FIND ... IN TABLE or READ TABLE ... TRANSPORTING NO FIELDS. a) See the source code excerpt from the model solution. 3. Remove the current line from lt_comps if the corresponding table name is not contained in import parameter it_comp_names. Hint: Use the abbreviated syntax for index access in loops here.

a) See the source code excerpt from the model solution. 4. To generate an RTTI type description object for a new structure type, call the CREATE method of class CL_ABAP_STRUCTDESCR. Pass the reduced component list to the method. Create a data object with a suitable type for the return parameter (suggested name: lo_struct_new). a) See the source code excerpt from the model solution. 5. To generate an RTTI type description object for a new table type, call the CREATE method of class CL_ABAP_TABLEDESCR. Pass the reference to the RTTI object for the new structure type. Leave all the optional parameters set to their default values. Transfer the result of the method call directly to return parameter ro_table_def of method create_table_type. a) See the source code excerpt from the model solution.

Task 6 Go back to your executable program ZBC402_##_RTTC. Call method create_table_type to generate a table type according to the requirements of the user. Use a new data type when you generate the data object dynamically.

550

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

Change the SELECT statement so that it reads only those fields from the database that are contained in the line type of the internal table.

Hint: Method write_headers still outputs the headers for all the columns in the table. You either work without the headers completely or use method write_headers_by_data from class CL_BC402_DYS_RTTI_HEADERS. This method analyzes the actual line type of an internal table and outputs the column headers for it. 1. Call method create_table_type in the program directly after the call of function module  BC402_SELECT_COMPONENTS. Pass the name of the database table and the list of components that the user selected to the method create_table_type. a) See the source code excerpt from the model solution. 2. Change the type in the CREATE DATA statement. Use the TYPE HANDLE addition to use the newly generated table type. a) See the source code excerpt from the model solution. 3. Change the SELECT statement. Use the list of component names as a dynamic field list. Hint: Alternatively, use the INTO CORRESPONDING FIELDS OF TABLE addition.

4. Activate and test your program. a) Perform this step as usual. Method create_table_type (Class CL_BC402_DYS_RTTC) METHOD create_table_type. DATA: lo_struct TYPE REF TO cl_abap_structdescr, lo_struct_new TYPE REF TO cl_abap_structdescr. DATA: lt_comps TYPE cl_abap_structdescr=>component_table. FIELD-SYMBOLS: LIKE LINE OF lt_comps. * get description of transparent table (=structure type) lo_struct ?= cl_abap_typedescr=>describe_by_name( iv_tabname ). * get list of components (including component types) lt_comps = lo_struct->get_components( ). LOOP AT lt_comps ASSIGNING .

© Copyright . All rights reserved.

551

Unit 11: Dynamic Programming

FIND -name IN TABLE it_comp_names. IF sy-subrc 0. DELETE lt_comps. ENDIF. ENDLOOP. * alternatve solution with read table * remove all components but the requested ones * LOOP AT lt_comps ASSIGNING . * READ TABLE it_comp_names * TRANSPORTING NO FIELDS * WITH TABLE KEY table_line = -name. * IF sy-subrc 0. * DELETE lt_comps . * ENDIF. * * ENDLOOP. * create new structure type with the remaining components lo_struct_new = cl_abap_structdescr=>create( p_components = lt_comps ). * create table type with this new structure type as line type ro_tabledescr = cl_abap_tabledescr=>create( p_line_type = lo_struct_new ). ENDMETHOD. Executable Program BC402_DYS_RTTC REPORT

bc402_dys_rttc MESSAGE-ID bc402.

DATA: gr_table

TYPE REF TO data.

DATA: gv_tabname TYPE string. DATA: gt_comp_names TYPE string_table, go_table TYPE REF TO cl_abap_tabledescr. FIELD-SYMBOLS: TYPE ANY TABLE. SELECTION-SCREEN COMMENT 1(80) text-sel. PARAMETERS pa_tab TYPE dd02l-tabname DEFAULT 'SPFLI'. PARAMETERS: pa_nol TYPE i DEFAULT '100'. START-OF-SELECTION. gv_tabname = pa_tab. CALL FUNCTION 'BC402_SELECT_COMPONENTS' EXPORTING iv_tabname = gv_tabname

552

© Copyright . All rights reserved.

Lesson: Creating Data Types, Data Objects, and Objects at Runtime

IMPORTING et_comp_names EXCEPTIONS type_not_found no_structure no_ddic_type

= gt_comp_names = 1 = 2 = 3.

CASE sy-subrc. WHEN 1. MESSAGE e050 WITH gv_tabname. WHEN 2. MESSAGE e051 WITH gv_tabname. WHEN 3. MESSAGE e052 WITH gv_tabname. ENDCASE. go_table = cl_bc402_dys_rttc=>create_table_type( iv_tabname = gv_tabname it_comp_names = gt_comp_names ). CREATE DATA gr_table TYPE HANDLE go_table. ASSIGN gr_table->* TO . TRY.

SELECT (gt_comp_names) FROM (gv_tabname) INTO TABLE UP TO pa_nol ROWS. CATCH cx_sy_dynamic_osql_error. MESSAGE e061. ENDTRY. CALL METHOD cl_bc402_dys_rtti_headers=>write_headers_by_data EXPORTING it_table = EXCEPTIONS no_structure = 1 no_ddic_type = 2 component_not_elem = 3. CASE sy-subrc. WHEN 1. MESSAGE e050 WITH gv_tabname. WHEN 2. MESSAGE e051 WITH gv_tabname. WHEN 3. MESSAGE e053 WITH gv_tabname. ENDCASE. cl_bc402_dys_gen_types=>write_any_table( ).

© Copyright . All rights reserved.

553

Unit 11: Dynamic Programming

LESSON SUMMARY You should now be able to:

554



Create objects (instances) at runtime



Create data objects at runtime



Create data types at runtime

© Copyright . All rights reserved.

Unit 11 Learning Assessment

1. The INDEX TABLE is a special generic data type that is only compatible with internal tables. Determine whether this statement is true or false. X

True

X

False

2. Field symbols are pointers that you assign to data objects statically. Determine whether this statement is true or false. X

True

X

False

3. You can replace data objects in operand positions directly by character-type data objects in parentheses by using the ASSIGN statement for the data object to which you need to assign the field symbol. Determine whether this statement is true or false. X

True

X

False

4. When you assign values between two reference variables with different types, you perform what is called a “cast assignment”. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

555

Unit 11: Learning Assessment

5. Which of the following classes do you instantiate and use to describe specific types? Choose the correct answers. X

A CL_ABAP_ELEMDESCR

X

B CL_ABAP_INTFDESCR

X

C CL_ABAP_STRUCTDESCR

X

D CL_ABAP_RTTI

6. The description classes for object types provide navigation methods for determining the details of a used type. Determine whether this statement is true or false. X

True

X

False

7. To generate objects at runtime, the static type of the reference variable must be compatible with the class. Determine whether this statement is true or false. X

True

X

False

8. If you use character-type data objects in parentheses, you can also define the data type for generated data objects dynamically. Determine whether this statement is true or false. X

True

X

False

9. With the HANDLE addition, the CREATE DATA statement creates a data object whose data type is described by an RTTS type object. Determine whether this statement is true or false.

556

X

True

X

False

© Copyright . All rights reserved.

Unit 11 Learning Assessment - Answers

1. The INDEX TABLE is a special generic data type that is only compatible with internal tables. Determine whether this statement is true or false. X

True

X

False

2. Field symbols are pointers that you assign to data objects statically. Determine whether this statement is true or false. X

True

X

False

3. You can replace data objects in operand positions directly by character-type data objects in parentheses by using the ASSIGN statement for the data object to which you need to assign the field symbol. Determine whether this statement is true or false. X

True

X

False

4. When you assign values between two reference variables with different types, you perform what is called a “cast assignment”. Determine whether this statement is true or false. X

True

X

False

© Copyright . All rights reserved.

557

Unit 11: Learning Assessment - Answers

5. Which of the following classes do you instantiate and use to describe specific types? Choose the correct answers. X

A CL_ABAP_ELEMDESCR

X

B CL_ABAP_INTFDESCR

X

C CL_ABAP_STRUCTDESCR

X

D CL_ABAP_RTTI

6. The description classes for object types provide navigation methods for determining the details of a used type. Determine whether this statement is true or false. X

True

X

False

7. To generate objects at runtime, the static type of the reference variable must be compatible with the class. Determine whether this statement is true or false. X

True

X

False

8. If you use character-type data objects in parentheses, you can also define the data type for generated data objects dynamically. Determine whether this statement is true or false. X

True

X

False

9. With the HANDLE addition, the CREATE DATA statement creates a data object whose data type is described by an RTTS type object. Determine whether this statement is true or false.

558

X

True

X

False

© Copyright . All rights reserved.

View more...

Comments

Copyright ©2017 KUPDF Inc.
SUPPORT KUPDF