ABAP,Java和JavaScript的local class

Local class in ABAP

Suppose I have a global class with a public method ADD with following signature. I would like to implement with a local class inside this global class.

ABAP,Java和JavaScript的local class_第1张图片

The local class could be created by clicking button “Local Definitions/Implementions”:

ABAP,Java和JavaScript的local class_第2张图片

Now in my global class I can just delegate the ADD implementation to the local class. Notice that even ADD method is marked as public, it is still displayed as a red light in class builder, which makes sense since this ADD method in local class is not visible to outside consumers.

ABAP,Java和JavaScript的local class_第3张图片

Local class in ABAP in widely used in the following scenarios:

(1) ABAP unit test class
(2) The pre/post exit enhancement of class method are technically implemented via a local class in enhancement include.
For example, once you click the “Post-Exit” button below,

ABAP,Java和JavaScript的local class_第4张图片

You will see the source code as below, the local class LCL_ZCL_JERRY_POSTEXIT is automatically generated by class builder.

CLASS LCL_ZCL_JERRY_POSTEXIT DEFINITION DEFERRED.
CLASS CL_JERRY_TOOL DEFINITION LOCAL FRIENDS LCL_ZCL_JERRY_POSTEXIT.
CLASS LCL_ZCL_JERRY_POSTEXIT DEFINITION.
PUBLIC SECTION.
CLASS-DATA OBJ TYPE REF TO LCL_ZCL_JERRY_POSTEXIT. "#EC NEEDED
DATA CORE_OBJECT TYPE REF TO CL_JERRY_TOOL . "#EC NEEDED
 INTERFACES  IPO_ZCL_JERRY_POSTEXIT.
  METHODS:
   CONSTRUCTOR IMPORTING CORE_OBJECT
     TYPE REF TO CL_JERRY_TOOL OPTIONAL.
ENDCLASS.
CLASS LCL_ZCL_JERRY_POSTEXIT IMPLEMENTATION.
METHOD CONSTRUCTOR.
  ME->CORE_OBJECT = CORE_OBJECT.
ENDMETHOD.

METHOD IPO_ZCL_JERRY_POSTEXIT~GET_QUERY_RESULT.
*"------------------------------------------------------------------------*
*" Declaration of POST-method, do not insert any comments here please!
*"
*"class-methods GET_QUERY_RESULT
*"  importing
*"    !IV_COL_WRAPPER type ref to CL_BSP_WD_COLLECTION_WRAPPER
*"  changing
*"    value(RV_RESULT) type ref to IF_BOL_ENTITY_COL . "#EC CI_VALPAR
*"------------------------------------------------------------------------*
**************  define your own post enhancement here!!! **************

ENDMETHOD.
ENDCLASS.

(3) if an event handler in a given program is not intended to be reused by other programs, it could be defined as a local class within the program it is used – in this case it is not necessary to define a global class as event handler.

There are lots of such examples in ALV examples delivered by SAP, see program BCALV_GRID_DND_TREE as example.

ABAP,Java和JavaScript的local class_第5张图片

Inner Class in Java

The above example could simply be written in Java as well. In this example the inner class lcl_local does not follow Camel naming convention since I would like to highlight that it works exactly the same as the one in ABAP example.

public class LocalClassTest{
    public int add(int var1, int var2){
        return new lcl_local().add(var1, var2);
    }
    private class lcl_local { 
        public int add(int var1, int var2){
            return var1 + var2;
        }
    }
}

Just exactly the same as in ABAP, the local class could not be used outside the class where it is defined.

ABAP,Java和JavaScript的local class_第6张图片

One typical usecase of inner class in Java is the efficient implementation of a thread-safe singleton pattern, see sample code below:

public class Example {
    private static class StaticHolder {
        static final MySingleton INSTANCE = new MySingleton();
    }
 
    public static MySingleton getSingleton() {
        return StaticHolder.INSTANCE;
    }
}

“Local class” in JavaScript

I use double quote in title since the function object in JavaScript are not actual “class” concept in ABAP and Java.

Below source code is a simulation of private attributes & methods in JavaScript:

function createClass(conf){
    function _injectAttribute(fn){
        var prototype = fn.prototype;
        for(var publicName in publics){
            if(!publics.hasOwnProperty(publicName))
                continue;
            if(typeof publics[publicName]=="function")
                prototype[publicName] = function(publicName){
                    return function(){
                        return publics[publicName].apply(privates, arguments);
                    }
                }(publicName);
            else 
                prototype[publicName] = publics[publicName];
            if(!privates[publicName])
                privates[publicName] = prototype[publicName];
        }
        return fn;
    }
    var publics, privates;
        publics = conf.publics;
        privates = conf.privates || new Object();

    var fn = function(fn){
        return function(){
            return fn.apply(privates, arguments);
        };
    }(conf.constructor || new Function());

    return _injectAttribute(fn);
}

var MyClass = createClass({
    constructor:function(){
        console.log("constructor is called: " + this.message);
    },
    publics:{
        message:"Hello, World",
        sayJavaScript:function(){
            return this._message;
        },
        sayABAP:function(msg){
            return msg + ", " + this.ABAP();
        }
    },
    privates:{
        _message: "Hello, JavaScript",
        ABAP :function(){
            return "ABAP";
        }
    }
});

var myClassInstance = new MyClass();

console.log(myClassInstance.message);
console.log(myClassInstance.sayJavaScript());
console.log(myClassInstance.sayABAP("Hello"));
console.log(myClassInstance._message);
console.log(myClassInstance.ABAP());

ABAP,Java和JavaScript的local class_第7张图片

Testing shows it works as expected:

ABAP,Java和JavaScript的local class_第8张图片

Local function in ES6

In ES6 it is possible to define a class via syntax suger class:

class Developer {
    constructor(name, language) {
        this.workingLanguage = language;
        let _name = name;

        let _getName = function() { 
            return _name; 
        };
        this.getName = _getName;
    }
}

var Jerry = new Developer("Jerry", "Java");
var Ji = new Developer("Ji", "JavaScript");

console.log("Developer name: " + Jerry.getName());
console.log("Jerry's working language: " + Jerry.workingLanguage);
console.log("local function accessible? " + Jerry._getName);
console.log("Jerry's name: " + Jerry._name);

ABAP,Java和JavaScript的local class_第9张图片

Further reading

I have written a series of blogs which compare the language feature among ABAP, JavaScript and Java. You can find a list of them below:

要获取更多Jerry的原创文章,请关注公众号"汪子熙":

你可能感兴趣的:(abap,crm,erp,sap,saprfc)