类的使用

面向对象

1. 类与接口定义

1.1.类定义、实现

*类定义
CLASS C1 DEFINITION.
  PUBLIC SECTION.
    METHODS WRITE.

    METHODS ADD
      IMPORTING OPERAND TYPE I
      EXPORTING RESULT  TYPE I
      RAISING   CX_SY_ARITHMETIC_ERROR.
      
   METHODS CONNENT
      IMPORTING
        P1            TYPE C
        REFERENCE(P2) TYPE C DEFAULT 'b'
        VALUE(P3)     TYPE C OPTIONAL   "
      EXPORTING
        RESULT        TYPE CHAR3.

    METHODS METH1
      IMPORTING
        NAME          TYPE STRING
      RETURNING
        VALUE(RESULT) TYPE STRING.      
ENDCLASS.

CLASS C1 IMPLEMENTATION.
  METHOD WRITE.
    WRITE: 'WRITE C1',/.
  ENDMETHOD.

  METHOD ADD.
    RESULT = 1 + OPERAND.
  ENDMETHOD.
  
  METHOD CONNENT.
    CONCATENATE P1 P2 P3 INTO RESULT.
  ENDMETHOD.

  METHOD METH1.
    RESULT = |Hello { NAME }!|.
  ENDMETHOD.  
ENDCLASS.

1.2.接口定义、实现

*接口定义
INTERFACE I1.
  METHODS IMETH1.
ENDINTERFACE.

INTERFACE I2.
  METHODS IMETH1.
ENDINTERFACE.

CLASS C2 DEFINITION.
  PUBLIC SECTION.
    INTERFACES: I1,I2."可实现多个接口
ENDCLASS.

CLASS C2 IMPLEMENTATION.
  METHOD I1~IMETH1.
    WRITE: 'WRITE I1~IMETH1',/.
  ENDMETHOD.

  METHOD I2~IMETH1.
    WRITE: 'WRITE I2~IMETH1',/.
  ENDMETHOD.
ENDCLASS.

1.3.类、接口继承

*类继承
CLASS C3 DEFINITION INHERITING FROM C1.
  PUBLIC SECTION.
    METHODS WRITE1.
ENDCLASS.

CLASS C3 IMPLEMENTATION.
  METHOD WRITE1.
    WRITE: 'WRITE C3 SUB',/.
  ENDMETHOD.
ENDCLASS.

*接口继承
INTERFACE I3.
  METHODS M0.
ENDINTERFACE.
INTERFACE I4.
  "可以有相同的成员名,因为继承过来后,成员还是具有各自的命名空间,在实现时
  "被继承过来的叫 I3~M0,在这里的名为I4~M0,所以是不同的两个方法
  INTERFACES I3.
  METHODS M0.
  METHODS M1.
ENDINTERFACE.

1.4. 向下强转型 ?=

OREF1 =  OREF3. 	"向上自动转型

"拿开注释运行时抛异常,因为OREF1此时指向的对象不是C3,而是C1,所以能强转的前提是OREF1指向的是C3
"CREATE OBJECT OREF1.
OREF3 ?= OREF1.	"向下强转型

1.5. 方法

*简单调用
  CALL METHOD OREF1->ADD
    EXPORTING
      OPERAND = 1
    IMPORTING
      RESULT  = L_I.
  WRITE:L_I,/.

  CALL METHOD OREF1->CONNENT
    EXPORTING
      P1     = 'A'
*     P2     = 'B'		"首选 默认值
      P3     = 'C'		"可选的
    IMPORTING
      RESULT = L_C.
  WRITE:L_C,/.


  L_STR = NEW C1( )->METH1( CONV #( SY-UNAME ) ) .
  WRITE: L_STR,/.

1.6. 事件

CLASS C4 DEFINITION."事件源
  PUBLIC SECTION.
    EVENTS: E1 EXPORTING VALUE(P1) TYPE C,
            E2.

    CLASS-EVENTS CE1 EXPORTING VALUE(P2) TYPE I.

    METHODS TRIGGER."事件触发方法
ENDCLASS.

CLASS C4 IMPLEMENTATION.
  METHOD TRIGGER.
    RAISE EVENT:E1 EXPORTING P1 = 'A',
                E2,
                CE1 EXPORTING P2 = 1.
  ENDMETHOD.
ENDCLASS.

CLASS C5 DEFINITION."监听器:即事件处理器
  PUBLIC SECTION.
    "静态方法也可以处理非静态事件,此方法属于非静态处理器,只能采用非静态注册方式
    CLASS-METHODS H1 FOR EVENT E1 OF C4 IMPORTING P1 SENDER.
    "非静态方法处理非静态事件,此方法属于非静态处理器,只能采用非静态注册方式
    METHODS: H2 FOR EVENT E2 OF C4 IMPORTING SENDER,
      "非静态方法当然更可以处理静态事件,此方法属于静态处理器,只能采用静态注册方式
      H3 FOR EVENT CE1 OF C4 IMPORTING P2.
ENDCLASS.

CLASS C5 IMPLEMENTATION.
  METHOD H1 .
    WRITE: 'C5=>h1',/.
  ENDMETHOD.
  METHOD: H2.
    WRITE: 'C5->h2',/.
  ENDMETHOD.
  METHOD: H3.
    WRITE: 'C5->h3',/.
  ENDMETHOD.
ENDCLASS.

START-OF-SELECTION.

DATA: TRIGGER  TYPE REF TO C4,
        TRIGGER2 TYPE REF TO C4,
        HANDLER  TYPE REF TO C5.

  CREATE OBJECT TRIGGER.
  CREATE OBJECT TRIGGER2.
  CREATE OBJECT HANDLER.
  "由于h1、h2两个处理方法分别是用来处理非静态事件e1、e2的,所以只能采用实例注册方式
  SET HANDLER: C5=>H1 HANDLER->H2 FOR TRIGGER,
  "h3处理方法是用来处理静态事件ce1的,属于静态处理器,所以只能采用静态注册方式
              HANDLER->H3.
  TRIGGER->TRIGGER( ).
  "虽然trigger( )方法会触发 e1,e2,ce1 三种事件,但h1、h2未向实例trigger2注册,而h3属于静态处理器,与实例无关,即好比向所有实例注册过了一样
  TRIGGER2->TRIGGER( ).

posted @ 2020-11-02 15:58  花开半夏930420  阅读(103)  评论(0)    收藏  举报