matinal: Обзор асинхронного вызова функций SAP ABAP (3)
matinal: Обзор асинхронного вызова функций SAP ABAP (3)

При разработке приложений SAP большое внимание уделяется эффективности отчетов. Конечно, существует множество способов оптимизировать эффективность отчетов. Когда мы сталкиваемся с отчетами, которые требуют обработки большого объема данных, мы обнаруживаем, что после исчерпания всех оптимизированных операторов эффективность работы отчета все еще не может удовлетворить потребности пользователя. отделение.

Ниже я представляю метод, который может быть вам полезен. Параллельная обработка ABAP (принцип аналогичен многопоточности Java), она реализует параллельную обработку программ посредством асинхронных вызовов удаленных функций через интерфейс RFC.

Синтаксис для синхронного/асинхронного вызова функций:

Синхронизация (sRFC): ВЫЗОВ ФУНКЦИИ «ААА»;

Суть синхронных вызовов: программа выполняется в одном потоке;

     Асинхронный (aRFC): CALL FUNCTION 'AAA' STARTING NEWTASK <taskname> «Имя задачи

                                             DESTINATION IN GROUP <RFC Serve Group>

                                             PERFORMING <subroutine>ON END OF TASK。"Подпрограмма

Суть асинхронных вызовов: программа выполняется в несколько потоков;

При использовании параллельной обработки обычно возникают следующие возможные проблемы:

1. Фоновые задачи, созданные при повторных запусках, конфликтуют друг с другом.

2. Существует разница между конечным результатом, полученным при асинхронном вызове, и результатом синхронного вызова.

3. Фиксированный RFC Server Группа, такая как система = 'parallel_generators',Нет никакой гарантии, что программа будет работать на разных серверах.

Решение трех вышеуказанных проблем заключается в следующем:

1. Во избежание конфликта фоновых задач друг с другом и возникновения различий в выходных данных следует обеспечить, чтобы одна и та же программа могла использоваться только одним пользователем в один и тот же период времени.

Оккупировано. Поэтому добавление объектов в разработанную программу может решить проблему. (Настройки блокировки программы, как прилагается)

2. Анализ. Используйте режим вызова асинхронной функции в цикле LOOP и используйте SY-SUBRC = 0, чтобы определить, успешно ли запущена задача.

     Когда SY-SUBRC <> Когда 0, получается значение, возвращенное ранее запущенным процессом, но при этом возникает проблема: если N-й цикл точно равен

Процесс, назначенный программе, полностью занят, поэтому на этот раз запустить процесс задачи невозможно, в результате чего исходные данные невозможно получить с помощью функции.

цели, так что конечный результат имеет неполные данные и изменяющиеся значения.

Решение. Пожертвуйте некоторой производительностью, чтобы обеспечить целостность данных. Получите значение максимального количества запросов сервера в очереди через RZ12, LOOP.

При зацикливании подсчитайте, равно ли количество запущенных процессов = Макс. запросов в очереди. Если равно, получите ранее запущенные процессы.

Возвращаемое значение,а затем перезапустите процесс,Повторите это。Максимальное количество процессов, которые система выделяет каждой программе.> Max. requests in 

Очередь, но ограничение количества запущенных процессов до уровня Max.requests в очереди может обеспечить целостность результатов.

3. Как узнать количество параллельно запущенных процессов, установленное системой. С помощью RZ12 и дважды щелкнув текущую группу входа, вы можете просмотреть максимальное количество параллельных процессов?

Как показано ниже:

  Как правило, система прямо определяет<RFC Serve Group> =' parallel_generators ', как показано на рисунке выше, содержимое, соответствующее «группе серверов», получается через следующий логический сегмент, чтобы сохранить общность:

Определение переменной-DATA: g_classname Тип rzlli_apcl, «Имя группы серверов»

                           g_applserver   Type rzllitab-applserver."RFC Serve Group

Логика доступа к номеру — CALL 'C_SAPGPARAM' "#EC CI_CCALL ИДЕНТИФИКАЦИОННОЕ ПОЛЕ «ИМЯ» «rdisp/myname» Идентификатор «значения» хранится в файле g_applserver.

                   SELECT SINGLE classname 

                               FROM   rzllitab

                               INTO     g_classname   "Server Group Name

                            WHERE   applserver = g_applserver

                                                                                                                                                                                                                                    И  grouptype = 'S'.

Через приведенное выше описание вы можете подключить его через пример, например, вложение.

1. Получить сервисную группу

2. Асинхронный вызов функций

3. Подпрограммы обработки

4. Если вызванная подпрограмма не является стандартной для системы, вам необходимо определить необходимую подпрограмму логики обработки в SE37.

Язык кода:javascript
копировать
*&---------------------------------------------------------------------*
*& Report  ZMATINAL
*&----------------------------------------------------------------------*
*&----------------------------------------------------------------------*
*  Changer           Changed Date         Request  NO.        Dec.
*&----------------------------------------------------------------------*

report  zmatinal message-id zmess.

tables: mara,marc.

types: begin of gs_out,
        werks type Марк-Веркс, "фабрика"
        dispo type marc-dispo,"контроллер MRP
        matnr type marc-matnr,"Материал
        maktx type makt-maktx,"Описание материала
        meins type мара-мейнс, "единица
        matkl type мара-маткл, «Группа материалов
        labst type mard-labst, "Неограниченный запас NO-X
        zsupl type mard-labst, «Просроченный запас NO-X
        zreqd type mard-labst, «Требования NO-X истекли
        ztype type c,         "тип периода
        ztext type c length 20,"тип период
        dat01 type mard-labst, "Первый период
        dat02 type mard-labst, «Период-второй
        dat03 type mard-labst, «Период-третий
        dat04 type mard-labst, «Период-четвёртый
        dat05 type mard-labst, «Период-пять
        dat06 type mard-labst, «Период-шестой
        dat07 type mard-labst, "период семь
        dat08 type mard-labst, «Период-восьмой
        dat09 type mard-labst, «Период-девятый
        dat10 type mard-labst, «Период-десять
        dat11 type mard-labst, "Период-эвелен
        dat12 type mard-labst, «Период-двенадцатый
       end of gs_out,

       begin of gs_dtl,
        werks type Марк-Веркс, "фабрика"
        matnr type marc-matnr,"Материал
        zdate type sy-datum,  «Дата требования
        delb0 type t457t-delb0,"Элемент ППМ
        extra type mdez-extra,"Данные элемента ППМ
        mng01 type mdez-mng01,"Количество поступления или необходимое количество
       end of gs_dtl,

       begin of gs_marc,
        matnr type marc-matnr,"МатериалID
        werks type Марк-Веркс, "фабрика"
        dispo type marc-dispo,"контроллер MRP
        matkl type мара-маткл, «Группа материалов
        meins type мара-мейнс, "базовая единица"
       end of gs_marc,

       begin of gs_mard,
        matnr type mard-matnr,"Материал
        werks type Мард-Веркс, "фабрика"
        lgort type mard-lgort,"Местоположение инвентаря
        labst type mard-labst,"Подсчет запасов
       end of gs_mard,

       begin of gs_makt,
        matnr type makt-matnr,"Материал
        maktx type makt-maktx,"Описание материала
       end of gs_makt,

       begin of gs_task,
        matnr type marc-matnr,"Материал
        werks type Марк-Веркс, "фабрика"
        dispo type marc-dispo,"контроллер MRP
        matkl type мара-маткл, «Группа материалов
        meins type мара-мейнс, "единица
        maktx type makt-maktx,"Описание материала
        labst type mard-labst,"Инвентарь
        taskname type c length 12,
       end of gs_task.

data: gw_task type gs_task,
      gt_task type standard table of gs_task.

data: gw_out    type gs_out,
      gw_dtl    type gs_dtl,
      gw_mard   type gs_mard.

data: gt_out    type standard table of gs_out,
      gt_dtl    type standard table of gs_dtl,"подробнее alv
      gt_marc   type standard table of gs_marc,
      gt_marc_d type standard table of gs_marc,
      gt_makt   type standard table of gs_makt,
      gt_mard   type standard table of gs_mard,
      gt_mard_s type standard table of gs_mard.
data: gt_noxlog type standard table of znoxlog with header line.

field-symbols:<fs_out>  type gs_out,
              <fs_mard> type gs_mard,
              <fs_marc> type gs_marc,
              <fs_makt> type gs_makt,
              <fs_mrp>  type bapi_mrp_items,
              <fs>,
              <fs1>,
              <fs2>,
              <fs3>.

data: gt_mrp_items type standard table of bapi_mrp_items."Данные MRP_ITEMs


data: g_txt type c length 20,
      g_num type n length 2.
data: g_mondy type d,
      g_sundy type d.
data: g_post  type i.
data: g_mark  type c.

*****-------определение GRID_ALV
class lcl_alv definition deferred.
data: g_alv type ref to lcl_alv.
data: gt_fcat  type lvc_t_fcat,
      gw_fcat  type lvc_s_fcat,
      is_layo  type lvc_s_layo,
      is_vart  type disvariant.
data: g_grid1 type ref to cl_gui_alv_grid,
      g_custom_container1 type ref to cl_gui_custom_container,
      g_container1 type scrfname value 'GRID_01'.
data: ok_code type sy-ucomm,
      save_ok type sy-ucomm.

*-----------------------------------------------------------------------*
*DESC: определение асинхронной переменной.
*-----------------------------------------------------------------------*
data: g_taskname(12) type c, "task имя (имена запущенных одновременно задач должны оставаться уникальными)
      g_classname    type rzlli_apcl,   "Server Group Name
      g_applserver   type rzllitab-applserver."RFC Serve Group

data: snd_jobs type i,
      rcv_jobs type i,
      functioncall1(1) type c.

constants: done(1) type c value 'X',
           pnum    type i value 5.»Количество процессов

*----------------------------------------------------------------------*
*       CLASS LCL_ALV DEFINITION
*----------------------------------------------------------------------*
*
*----------------------------------------------------------------------*
class lcl_alv definition.
  public section.
    methods:
             create_object,
             fcat_setting,
             layo_setting,
             disp,
             main.

  private section.

endclass.                    "LCL_ALV DEFINITION

*----------------------------------------------------------------------*
*       CLASS LCL_ALV IMPLEMENTATION
*----------------------------------------------------------------------*
*
*----------------------------------------------------------------------*
class lcl_alv implementation.
  method create_object.
    if g_custom_container1 is initial.
      «Создать контейнер
      create object g_custom_container1
        exporting
          container_name              = g_container1
        exceptions
          cntl_error                  = 1
          cntl_system_error           = 2
          create_error                = 3
          lifetime_error              = 4
          lifetime_dynpro_dynpro_link = 5
          others                      = 6.
      if sy-subrc ne 0.
        message 'error1' type 'E'.
      endif.

      «Создать ИВЛ
      create object g_grid1
        exporting
          i_parent          = g_custom_container1
        exceptions
          error_cntl_create = 1
          error_cntl_init   = 2
          error_cntl_link   = 3
          error_dp_create   = 4
          others            = 5.
      if sy-subrc ne 0.
        message 'error2' type 'E'.
      endif.

    else.
      g_grid1->refresh_table_display( ).
    endif.

  endmethod.                    "CREATE_OBJECT

  method fcat_setting.
    perform frm_set_fcat.

  endmethod.                    "FCAT_SETTING

  method layo_setting.
    is_layo-zebra = 'X'."Чересстрочный цвет
    is_layo-sel_mode = 'А'.»необязательно
    is_layo-cwidth_opt = 'X'."Оптимизация отображения выходного столбца

    is_vart-report = sy-repid.
  endmethod.                    "LAYO_SETTING

  method disp.
    «Выход ИВЛ
    call method g_grid1->set_table_for_first_display
      exporting
        i_structure_name              = 'GS_DTL'
        is_variant                    = is_vart
        i_save                        = 'A'
        i_default                     = 'X'
        is_layout                     = is_layo
      changing
        it_outtab                     = gt_dtl[]
        it_fieldcatalog               = gt_fcat[]
                                                                                                                                                                                                                   "it_sort                       = gt_sort[]
      exceptions
        invalid_parameter_combination = 1
        program_error                 = 2
        too_many_lines                = 3
        others                        = 4.
    if sy-subrc ne 0.
      message 'error3' type 'E'.
    endif.

    call method cl_gui_control=>set_focus
      exporting
        control = g_grid1.
  endmethod.                    "DISP

  method main.
    me->create_object( ).
    me->fcat_setting( ).
    me->layo_setting( ).
    me->disp( ).
  endmethod.                    "MAIN

endclass.                    "LCL_ALV IMPLEMENTATION

*---------------------------------------------------------------------*
* DESC:ALV определение переменной
*---------------------------------------------------------------------*
type-pools: slis.
data: gt_fieldcat    type slis_t_fieldcat_alv with header line,  «Определите внутреннюю таблицу для хранения полей вывода
      gt_sort        type slis_t_sortinfo_alv,
      gw_layout      type slis_layout_alv, «Рабочая область, определяющая настройки макета ALV
      g_repid        like sy-repid.        «Определите переменную имени текущей программы системы
data: gw_stru_disvar type disvariant,        "ALV формат отображения
      gt_events      type slis_t_event.      "ALV событие

*-----------------------------------------------------------------------*
*DESC: выбор разрешения экрана.
*-----------------------------------------------------------------------*
selection-screen begin of block blk with frame title text-001.
select-options:s_werks for marc-werks обязательный, "фабричный"
               s_matnr for marc-matnr,"Материал
               s_dispo for marc-dispo обязательно,"контролер MRP
               s_matkl for мара-маткл."Группа материалов
select-options:s_lgort for marc-lgpro без дисплея."NO-X в наличии
parameters: p_date type mara-ersda default sy-datum обязательно."Дата начала
selection-screen end of block blk.

*-----------------------------------------------------------------------*
*INITIALIZATION
*-----------------------------------------------------------------------*
initialization.
  perform frm_init.

*-----------------------------------------------------------------------*
*START-OF-SELECTION
*-----------------------------------------------------------------------*
start-of-selection.
  perform frm_status(zpercent) using 10 «Чтение других связанных данных...».
  perform frm_get_date."Получить начальное значение расчетного периода
  perform frm_get_data."Получить основные данные
  if g_mark eq 'X'.
    stop.
  else.
    perform frm_set_lock."Установить блокировку
    perform frm_fill_alv.
    perform frm_set_unlock."Разблокировать
    perform frm_get_event.
    perform frm_init_layout.
    perform frm_sort_build changing gt_sort.
    perform frm_fcat_setting.
    perform frm_output tables gt_out.
  endif.


*&---------------------------------------------------------------------*
*&      Form  frm_init
*&---------------------------------------------------------------------*
*       инициализация
*----------------------------------------------------------------------*
form frm_init.
  clear: gt_noxlog,g_mondy,g_sundy.

  "Инициализация Местоположение склада NO-X
  select *
    into table gt_noxlog
    from znoxlog.

  loop at gt_noxlog.
    s_lgort-low = gt_noxlog-lgort.
    s_lgort-option = 'EQ'.
    s_lgort-sign = 'I'.
    append s_lgort.
  endloop.

endform.                    "frm_init

*&---------------------------------------------------------------------*
*&      Form  frm_get_date
*&---------------------------------------------------------------------*
*       Получить дату
*----------------------------------------------------------------------*
form frm_get_date.
  «Получить неделю и время даты начала
  call function 'GET_WEEK_INFO_BASED_ON_DATE'
    exporting
      date   = p_date
    importing
      monday = g_mondy
      sunday = g_sundy.

  g_mondy = p_date.
endform.                    "frm_init

*&---------------------------------------------------------------------*
*&      Form  FRM_get_data
*&---------------------------------------------------------------------*
*       Получить основные данные
*----------------------------------------------------------------------*
form frm_get_data.
  «По условиям ввода в таблицы MARC и MARA Получить основные данные
  select a~matnr "материалы
         a~werks "фабрика
         a~dispo «контролер ППМ»
         b~matkl "материалы Группа
         b~meins "единица
    into table gt_marc
    from marc as a join mara as b on a~matnr = b~matnr
    where a~matnr in s_matnr
      and a~werks in s_werks
      and a~dispo in s_dispo
      and a~lvorm ne 'X'
      and a~mmsta ne '99'
      and b~matkl in s_matkl.

  if gt_marc is not initial.

    «Получить описание материала
    gt_marc_d = gt_marc.
    sort: gt_marc_d by matnr.
    delete adjacent duplicates from gt_marc_d comparing matnr.

    select matnr "материалы
           maktx "материалыописывать
      into table gt_makt
      from makt
      for all entries in gt_marc_d
      where matnr = gt_marc_d-matnr
        and spras = '1'.

    "По внутренней таблице gt_marc получить инвентарный номер из таблицы MARD
    select matnr "материалы
           werks "фабрика
           lgort «Место хранения инвентаря
           labst "в наличии
      into table gt_mard
      from mard
      for all entries in gt_marc
      where matnr = gt_marc-matnr
        and werks = gt_marc-werks
        and lgort in s_lgort
        and diskz ne '1'.

    "Краткое содержание
    loop at gt_mard assigning <fs_mard>.
      clear:gw_mard.
      move <fs_mard>-matnr to gw_mard-matnr."материалы
      move <fs_mard>-werks to gw_mard-werks."фабрика
      move <fs_mard>-labst to gw_mard-labst."в наличии
      collect gw_mard into gt_mard_s.
    endloop.
  else.
    g_mark = 'X'.
    message s006(zppmess) display like 'E'.
  endif.

endform.                    "FRM_get_data

*&---------------------------------------------------------------------*
*&      Form  frm_fill_alv
*&---------------------------------------------------------------------*
*       Заполнение вывода ALV
*----------------------------------------------------------------------*
form frm_fill_alv.
  data: l_lgort   type mard-lgort,"в наличииточечная переменная
        l_count   type я, "столбец
        l_mondy   type д, "понедельник"
        l_sundy   type д, "выходные
        l_num(2)  type n,
        l_txt(20) type c.
  data: l_labst   type mard-labst,"Инвентарь
        l_zsupl   type mard-labst,"поставка
        l_zreqd   type mard-labst."Требования
  data: lt_mrp_01 type standard table of bapi_mrp_items,"Истек срок годности Calculation-NO-X
        lt_mrp_02 type standard table of bapi_mrp_items,"Требования Calculate-NO-X истекли
        lt_mrp_03 type standard table of bapi_mrp_items,"Рассчитайте подачу NO-X, соответствующую столбцу
        lt_mrp_04 type standard table of bapi_mrp_items."Рассчитайте требования NO-X, соответствующие столбцу

  sort: gt_makt   by matnr,
        gt_mard_s by matnr werks,
        gt_marc   by matnr werks.

  «Временная переменная
  data:mess(40) type c,        «Сообщение об ошибке одновременного выполнения
       open_task_num type i.   «Количество задач для запуска
  data:l_tabix  type sy-tabix, "индексная переменная
       l_lines  type i,        «Общее количество строк
       l_counts type p.


  "Получать RFC Serve Group name         Start--*
  «Общее системное имя g_classname по умолчанию = 'parallel_generators', но для общности получите его следующим образом
  call 'C_SAPGPARAM'                                      "#EC CI_CCALL
    id 'NAME'  field 'rdisp/myname'
    id 'VALUE' field g_applserver.

  select single classname
     from rzllitab
     into g_classname   "Server Group Name
    where applserver = g_applserver
      and grouptype = 'S'.   "S: группа серверов, пусто: группа входа
  "Получать RFC Serve Group name         End--*

  clear: open_task_num,l_lines.

  describe table gt_marc lines l_lines.
  l_counts = l_lines.

  loop at gt_marc assigning <fs_marc>.
    clear: gw_out,lt_mrp_01,lt_mrp_02,lt_mrp_03,lt_mrp_04,
           l_labst,l_zsupl,l_zreqd.
    l_tabix = sy-tabix.

    perform frm_percent(zpercent) using sy-tabix l_counts ''.
    move <fs_marc>-matnr to gw_out-matnr."материалы
    move <fs_marc>-werks to gw_out-werks."фабрика
    move <fs_marc>-dispo to gw_out-dispo.«контролер ППМ»
    move <fs_marc>-matkl to gw_out-matkl."материалы Группа

    "единица Конвертировать
    call function 'CONVERSION_EXIT_CUNIT_OUTPUT'
      exporting
        input  = <fs_marc>-meins
      importing
        output = gw_out-meins.

    «Получить описание материала
    read table gt_makt assigning <fs_makt> with key matnr = <fs_marc>-matnr binary search.
    if sy-subrc eq 0.
      move <fs_makt>-maktx to gw_out-maktx.
    endif.

    "ПолучатьNO-Xнеограниченный инвентарь
    read table gt_mard_s assigning <fs_mard> with key matnr = <fs_marc>-matnr binary search.
    if sy-subrc eq 0.
      move <fs_mard>-labst to gw_out-labst.
    endif.

*--Оптимизация, асинхронный вызов для получения данных,
    «Сгенерировать имя задачи = 'Task' + sy-tabix   Start--*
    move l_tabix to g_taskname.
    condense g_taskname.
    concatenate 'Task' g_taskname into g_taskname.
    «Сгенерировать имя задачи = 'Task' + sy-tabix   End--*

    clear: gw_task.
    gw_task-matnr = <fs_marc>-matnr.
    gw_task-werks = <fs_marc>-werks.
    gw_task-dispo = <fs_marc>-dispo.
    gw_task-matkl = <fs_marc>-matkl.
    gw_task-meins = gw_out-meins.
    gw_task-maktx = gw_out-maktx.
    gw_task-labst = gw_out-labst.
    gw_task-taskname  = g_taskname.
    append gw_task to gt_task.

*   асинхронныйвызовфункция    Start--*
    call function 'BAPI_MATERIAL_STOCK_REQ_LIST' starting new task g_taskname
        destination in group g_classname
        performing frm_subroutine_done on end of task "Подпрограмма
*      Просто поместите сюда параметр EXPORTING функции и другие параметры подпрограммы.
        exporting
          material         = <fs_marc>-matnr
          plant            = <fs_marc>-werks
          get_item_details = 'X'
          get_ind_lines    = 'X'
*       Стандартное системное сообщение об ошибке
        exceptions
          communication_failure = 1  message mess
          system_failure        = 2  message mess
          resource_failure      = 3.

    if sy-subrc = 0.
      snd_jobs = snd_jobs + 1.
    endif.
*   асинхронныйвызовфункция     End--*

    open_task_num = open_task_num + 1.   «Записать количество запущенных процессов

    if open_task_num = pnum.
*     Получите результаты, возвращаемые параллельными процессами
      wait until rcv_jobs >= snd_jobs.

      clear:open_task_num,rcv_jobs,snd_jobs.
      free:gt_task.
    else.
      if l_tabix = l_lines.
*     Получите результаты, возвращаемые параллельными процессами
        wait until rcv_jobs >= snd_jobs.

        clear:open_task_num,rcv_jobs,snd_jobs.
        free:gt_task.
      endif.
    endif.

  endloop.

endform.                    "frm_fill_alv

*&---------------------------------------------------------------------*
*&      Form  frm_subroutine_done
*&---------------------------------------------------------------------*
*      подпрограмма асинхронной обработки
*----------------------------------------------------------------------*
*      -->G_TASKNAME text
*----------------------------------------------------------------------*
form frm_subroutine_done using g_taskname.
  data: l_lgort   type mard-lgort,"в наличииточечная переменная
        l_auffx   type plaf-auffx,"фиксированный логотип
        l_count   type я, "столбец
        l_mondy   type д, "понедельник"
        l_sundy   type д, "выходные
        l_num(2)  type n,
        l_txt(20) type c.
  data: l_labst   type mard-labst,"Инвентарь
        l_zsupl   type mard-labst,"поставка
        l_zreqd   type mard-labst."Требования
  data: l_mark1   type c,
        l_mark2   type c,
        l_mark3   type c,
        l_mark4   type c,
        l_lines   type i.
  data: lt_mrp_01 type standard table of bapi_mrp_items,"Истек срок годности Calculation-NO-X
        lt_mrp_02 type standard table of bapi_mrp_items,"Требования Calculate-NO-X истекли
        lt_mrp_03 type standard table of bapi_mrp_items,"Рассчитайте подачу NO-X, соответствующую столбцу
        lt_mrp_04 type standard table of bapi_mrp_items."Рассчитайте требования NO-X, соответствующие столбцу

  rcv_jobs = rcv_jobs + 1.  ""Receiving data

  receive results from function 'BAPI_MATERIAL_STOCK_REQ_LIST'
    tables
      mrp_items        = gt_mrp_items.

  read table gt_task into gw_task with key taskname = g_taskname binary search.
  if sy-subrc eq 0.
    clear:l_mark1,l_mark2,l_mark3,l_mark4.

    gw_out-matnr = gw_task-matnr."материалы
    gw_out-werks = gw_task-werks."фабрика
    gw_out-dispo = gw_task-dispo.
    gw_out-meins = gw_task-meins.
    gw_out-maktx = gw_task-maktx.
    gw_out-labst = gw_task-labst.

    delete gt_mrp_items where ( mrp_element_ind = 'WB' and rec_reqd_qty is initial ).

    if gt_mrp_items is initial and gw_out-labst is initial. «Если MD04 пуст
      "CONTINUE.
    else.

      lt_mrp_01 = lt_mrp_02 = gt_mrp_items.

      «Просроченный запас Calculate-NO-X
      delete lt_mrp_01 where ( avail_date is initial ) or ( avail_date ge p_date ).
      delete lt_mrp_01 where plngsegno is not initial or plus_minus ne '+' or rec_reqd_qty is initial.

      loop at lt_mrp_01 assigning <fs_mrp>.
        if <fs_mrp>-storage_loc in s_lgort.
          if <fs_mrp>-mrp_element_ind = 'PA' and <fs_mrp>-firmed ne 'X'.
            continue.
          else.
            gw_out-zsupl = gw_out-zsupl + <fs_mrp>-rec_reqd_qty.
          endif.
        endif.
      endloop.

      «Требования к сроку годности Calculate-NO-X
      delete lt_mrp_02 where ( avail_date is initial ) or ( avail_date ge p_date ).
      delete lt_mrp_02 where plngsegno is not initial or plus_minus ne '-' or rec_reqd_qty is initial.

      loop at lt_mrp_02 assigning <fs_mrp>.
        clear:l_lgort,l_auffx.

        case <fs_mrp>-order_type.
          when «ВВ».»Аутсорсинг закупок
            «Идите к столу ЭКПО, чтобы получить инвентарь, удовлетворяющий NO-X.
            select single lgort
              into l_lgort
              from ekpo
              where ebeln = <fs_mrp>-source_no
                and ebelp = <fs_mrp>-source_item
                and lgort in s_lgort.

            if sy-subrc eq 0.
              gw_out-zreqd = gw_out-zreqd + <fs_mrp>-rec_reqd_qty.
            endif.

          when 'СБ'».Плановый заказ-нижний уровень
            «Перейдите к столу PLAF, чтобы получить инвентарь, соответствующий NO-X.
            select single lgort auffx
              into (l_lgort,l_auffx)
              from plaf
              where plnum = <fs_mrp>-source_no
                and lgort in s_lgort.

            if sy-subrc eq 0.
              if l_auffx eq «X». Исправлено.
                gw_out-zreqd = gw_out-zreqd + <fs_mrp>-rec_reqd_qty.
              endif.
            endif.

          when 'AR'."Резервирование производственного заказа
            «Перейдите к столу AFPO, чтобы получить инвентарь, соответствующий NO-X.
            select single lgort
              into l_lgort
              from afpo
              where aufnr = <fs_mrp>-mrp_no12
                and lgort in s_lgort.

            if sy-subrc eq 0.
              gw_out-zreqd = gw_out-zreqd + <fs_mrp>-rec_reqd_qty.
            endif.

          when others.
        endcase.
      endloop.

      «Определите один
      if gw_out-labst is initial and gw_out-zsupl is initial and gw_out-zreqd is initial.
        l_mark1 = 'X'.
      endif.

      "вычислить-столбец
      clear:l_count.
      do 3 times.
        l_count = l_count + 1.
        case l_count.
          when 1. Питание NO-X соответствует «вычислить-столбец».
            clear:g_num.
            l_mondy = g_mondy.
            l_sundy = g_sundy.
            gw_out-ztype = 'A'.
            gw_out-ztext = «Поставка NO-X».
            do 12 times.
              clear:g_txt.
              g_num = g_num + 1.
              g_txt = |GW_OUT-DAT{ g_num }|.
              assign (g_txt) to <fs>.

              lt_mrp_03 = gt_mrp_items.
              delete lt_mrp_03 where ( avail_date gt l_sundy ) or ( avail_date lt l_mondy ).
              delete lt_mrp_03 where plngsegno is not initial or plus_minus ne '+' or rec_reqd_qty is initial.

              loop at lt_mrp_03 assigning <fs_mrp>.
                if <fs_mrp>-storage_loc in s_lgort.
                  if <fs_mrp>-mrp_element_ind = 'PA' and <fs_mrp>-firmed ne 'X'.
                    continue.
                  else.
                    <fs> = <fs> + <fs_mrp>-rec_reqd_qty.
                  endif.
                endif.
              endloop.
              l_mondy = l_sundy + 1.
              l_sundy = l_sundy + 7.

              «Идентифицирует два, пока один из столбцов не пуст
              if <fs> is not initial.
                l_mark2 = 'X'.
              endif.
            enddo.
            append gw_out to gt_out.
            clear:gw_out-labst,gw_out-zsupl,gw_out-zreqd.

          when 2. Требования NO-X, соответствующие «вычислить-столбец».
            clear:g_num,gw_out-dat01,gw_out-dat02,gw_out-dat03,gw_out-dat04,gw_out-dat05,gw_out-dat06,
                        gw_out-dat07,gw_out-dat08,gw_out-dat09,gw_out-dat10,gw_out-dat11,gw_out-dat12.
            l_mondy = g_mondy.
            l_sundy = g_sundy.
            gw_out-ztype = 'B'.
            gw_out-ztext = «Спрос на NO-X».
            do 12 times.
              clear:g_txt.
              g_num = g_num + 1.
              g_txt = |GW_OUT-DAT{ g_num }|.
              assign (g_txt) to <fs>.

              lt_mrp_04 = gt_mrp_items.
              delete lt_mrp_04 where ( avail_date gt l_sundy ) or ( avail_date lt l_mondy ).
              delete lt_mrp_04 where plngsegno is not initial or plus_minus ne '-' or rec_reqd_qty is initial.

              loop at lt_mrp_04 assigning <fs_mrp>.
                clear:l_lgort,l_auffx.

                case <fs_mrp>-order_type.
                  when «ВВ».»Аутсорсинг закупок
                    «Идите к столу ЭКПО, чтобы получить инвентарь, удовлетворяющий NO-X.
                    select single lgort
                      into l_lgort
                      from ekpo
                      where ebeln = <fs_mrp>-source_no
                        and ebelp = <fs_mrp>-source_item
                        and lgort in s_lgort.

                    if sy-subrc eq 0.
                      <fs> = <fs> + <fs_mrp>-rec_reqd_qty.
                    endif.

                  when 'СБ'».Плановый заказ-нижний уровень
                    «Перейдите к столу PLAF, чтобы получить инвентарь, соответствующий NO-X.
                    select single lgort auffx
                      into (l_lgort,l_auffx)
                      from plaf
                      where plnum = <fs_mrp>-source_no
                        and lgort in s_lgort.

                    if sy-subrc eq 0.
                      if l_auffx = 'X'.
                        <fs> = <fs> + <fs_mrp>-rec_reqd_qty.
                      endif.
                    endif.

                  when 'AR'."Резервирование производственного заказа
                    «Перейдите к столу AFPO, чтобы получить инвентарь, соответствующий NO-X.
                    select single lgort
                      into l_lgort
                      from afpo
                      where aufnr = <fs_mrp>-mrp_no12
                        and lgort in s_lgort.

                    if sy-subrc eq 0.
                      <fs> = <fs> + <fs_mrp>-rec_reqd_qty.
                    endif.

                  when others.
                endcase.
              endloop.
              l_mondy = l_sundy + 1.
              l_sundy = l_sundy + 7.

              «Идентифицирует три, пока один из столбцов не пуст
              if <fs> is not initial.
                l_mark3 = 'X'.
              endif.
            enddo.
            append gw_out to gt_out.

          when 3. «Рассчитать рекомендуемое количество поставки NO-X».
            clear:g_num,gw_out-dat01,gw_out-dat02,gw_out-dat03,gw_out-dat04,gw_out-dat05,gw_out-dat06,
                        gw_out-dat07,gw_out-dat08,gw_out-dat09,gw_out-dat10,gw_out-dat11,gw_out-dat12.
            gw_out-ztype = 'C'.
            gw_out-ztext = «Рекомендуемый объем поставки NO-X».

            do 12 times.
              clear:g_txt,l_num,l_txt.
              g_num = g_num + 1.
              g_txt = |GW_OUT-DAT{ g_num }|.
              assign (g_txt) to <fs>.

              if g_num = 01."Первый столбец
                l_num = g_num.
                «Поставка NO-X
                read table gt_out assigning <fs_out> with key matnr = gw_out-matnr
                                                              werks = gw_out-werks
                                                              ztype = 'A'.
                if sy-subrc eq 0.
                  l_txt = |<FS_OUT>-DAT{ l_num }|.
                  assign (l_txt) to <fs1>.
                  l_labst = <fs_out>-labst."в наличии
                  l_zsupl = <fs_out>-zsupl."поставлять
                  l_zreqd = <fs_out>-zreqd."нуждаться
                endif.
                «Спрос на NO-X
                read table gt_out assigning <fs_out> with key matnr = gw_out-matnr
                                                              werks = gw_out-werks
                                                              ztype = 'B'.
                if sy-subrc eq 0.
                  l_txt = |<FS_OUT>-DAT{ l_num }|.
                  assign (l_txt) to <fs2>.
                endif.

                «Рекомендуемый объем поставки в первом столбце = неограниченный инвентарь + Просроченный запас - Просроченные требования + поставка первого столбца - Требования к первому столбцу
                <fs> = l_labst + l_zsupl - l_zreqd + <fs1> - <fs2>.
              else.
                l_num = g_num - 1.
                «Поставка NO-X
                read table gt_out assigning <fs_out> with key matnr = gw_out-matnr
                                                              werks = gw_out-werks
                                                              ztype = 'A'.
                if sy-subrc eq 0.
                  l_txt = |<FS_OUT>-DAT{ g_num }|.
                  assign (l_txt) to <fs1>.
                endif.
                «Спрос на NO-X
                read table gt_out assigning <fs_out> with key matnr = gw_out-matnr
                                                              werks = gw_out-werks
                                                              ztype = 'B'.
                if sy-subrc eq 0.
                  l_txt = |<FS_OUT>-DAT{ g_num }|.
                  assign (l_txt) to <fs2>.
                endif.

                «Рекомендуемое количество NO-X в предыдущем столбце
                l_txt = |GW_OUT-DAT{ l_num }|.
                assign (l_txt) to <fs3>.

                «Текущее рекомендуемое количество NO-X = Рекомендуемое количество поставки в предыдущем столбце + текущая поставка столбца - Текущие требования
                if <fs3> ge 0.
                  <fs> = abs( <fs3> ) + <fs1> - <fs2>.
                else.
                  <fs> = <fs1> - <fs2>.
                endif.

                «Определите, больше ли количество предложений 0. Если оно больше 0, очистите его; в противном случае примите абсолютное значение
                if g_num = 12. «В последней петле нам нужно привязать два последних столбика.
                  if <fs> gt 0.
                    clear <fs>.
                  else.
                    <fs> = abs( <fs> ).
                  endif.

                  if <fs3> gt 0.
                    clear <fs3>.
                  else.
                    <fs3> = abs( <fs3> ).
                  endif.
                иначе." В противном случае просто судите по предыдущему столбцу
                  if <fs3> ge 0.
                    clear <fs3>.
                  else.
                    <fs3> = abs( <fs3> ).
                  endif.
                endif.

              endif.

              «Идентифицирует четыре, пока один из столбцов не пуст
              if <fs> is not initial.
                l_mark4 = 'X'.
              endif.
            enddo.
            append gw_out to gt_out.
        endcase.
      enddo.

      «Удалить пустые записи
      if l_mark1 = 'X' and l_mark2 is initial and l_mark3 is initial and l_mark4 is initial.
        describe table gt_out lines l_lines.
        delete gt_out index l_lines.
        delete gt_out index l_lines - 1.
        delete gt_out index l_lines - 2.
      endif.
    endif.
  endif.

endform.                    "frm_subroutine_done



*&---------------------------------------------------------------------*
*&      Form  frm_get_detail
*&---------------------------------------------------------------------*
*       text
*----------------------------------------------------------------------*
*      -->ALV        text
*      -->MATNR      text
*      -->WERKS      text
*      -->FNAME      text
*----------------------------------------------------------------------*
form frm_get_detail tables alv  structure gw_dtl
                    using matnr type marc-matnr
                          werks type marc-werks
                          fname type slis_fieldname
                          type  type c.

  data: lt_mrp type standard table of bapi_mrp_items.«Просроченный запас Calculate-NO-X
  data: l_lgort type mard-lgort,
        l_auffx type plaf-auffx,
        l_mondy type d,
        l_sundy type d,
        l_times type i.

                                                            "ПолучатьMD04
  call function 'BAPI_MATERIAL_STOCK_REQ_LIST'
    exporting
      material         = matnr
      plant            = werks
      get_item_details = 'X'
      get_ind_lines    = 'X'
    tables
      mrp_items        = lt_mrp.

  case fname+0(2).
    when «ЗС».»Поставка
      delete lt_mrp where ( avail_date is initial ) or ( avail_date ge p_date ).
      delete lt_mrp where plngsegno is not initial or plus_minus ne '+' or rec_reqd_qty is initial.

      loop at lt_mrp assigning <fs_mrp>.
        clear:gw_dtl.
        if <fs_mrp>-storage_loc in s_lgort.
          if <fs_mrp>-mrp_element_ind = 'PA' and <fs_mrp>-firmed ne 'X'.
            continue.
          else.
            gw_dtl-werks = werks.
            gw_dtl-matnr = matnr.
            gw_dtl-zdate = <fs_mrp>-avail_date."дата
            «Элементы ППМ
            select single delb0
              into gw_dtl-delb0
              from t457t
              where delkz = <fs_mrp>-mrp_element_ind
                and spras = '1'.

            «Элементы данные ППМ
            if <fs_mrp>-peggedrqmt is initial.
              gw_dtl-extra = |{ <fs_mrp>-mrp_no }/{ <fs_mrp>-mrp_pos }|.
            else.
              gw_dtl-extra = <fs_mrp>-peggedrqmt.
            endif.

            "количество
            gw_dtl-mng01 = <fs_mrp>-rec_reqd_qty.
            append gw_dtl to alv.
          endif.
        endif.
      endloop.

    when «ЗР».»Требования
      delete lt_mrp where ( avail_date is initial ) or ( avail_date ge p_date ).
      delete lt_mrp where plngsegno is not initial or plus_minus ne '-' or rec_reqd_qty is initial.

      loop at lt_mrp assigning <fs_mrp>.
        clear:gw_dtl,l_lgort,l_auffx.
        case <fs_mrp>-order_type.
          when «ВВ».»Аутсорсинг закупок
            «Идите к столу ЭКПО, чтобы получить инвентарь, удовлетворяющий NO-X.
            select single lgort
              into l_lgort
              from ekpo
              where ebeln = <fs_mrp>-source_no
                and ebelp = <fs_mrp>-source_item
                and lgort in s_lgort.

            if sy-subrc eq 0.
              gw_dtl-werks = werks.
              gw_dtl-matnr = matnr.
              gw_dtl-zdate = <fs_mrp>-avail_date."дата
              «Элементы ППМ
              select single delb0
                into gw_dtl-delb0
                from t457t
                where delkz = <fs_mrp>-mrp_element_ind
                  and spras = '1'.

              «Элементы данные ППМ
              if <fs_mrp>-peggedrqmt is initial.
                gw_dtl-extra = |{ <fs_mrp>-mrp_no }/{ <fs_mrp>-mrp_pos }|.
              else.
                gw_dtl-extra = <fs_mrp>-peggedrqmt.
              endif.

              "количество
              gw_dtl-mng01 = <fs_mrp>-rec_reqd_qty.
              append gw_dtl to alv.
            endif.

          when 'СБ'».Плановый заказ-нижний уровень
            «Перейдите к столу PLAF, чтобы получить инвентарь, соответствующий NO-X.
            select single lgort auffx
              into (l_lgort,l_auffx)
              from plaf
              where plnum = <fs_mrp>-source_no
                and lgort in s_lgort.

            if sy-subrc eq 0.
              if l_auffx eq 'X'.
                gw_dtl-werks = werks.
                gw_dtl-matnr = matnr.
                gw_dtl-zdate = <fs_mrp>-avail_date."дата
                «Элементы ППМ
                select single delb0
                  into gw_dtl-delb0
                  from t457t
                  where delkz = <fs_mrp>-mrp_element_ind
                    and spras = '1'.

                «Элементы данные ППМ
                if <fs_mrp>-peggedrqmt is initial.
                  gw_dtl-extra = |{ <fs_mrp>-mrp_no }/{ <fs_mrp>-mrp_pos }|.
                else.
                  gw_dtl-extra = <fs_mrp>-peggedrqmt.
                endif.

                "количество
                gw_dtl-mng01 = <fs_mrp>-rec_reqd_qty.
                append gw_dtl to alv.
              endif.
            endif.

          when 'AR'."Резервирование производственного заказа
            «Перейдите к столу AFPO, чтобы получить инвентарь, соответствующий NO-X.
            select single lgort
              into l_lgort
              from afpo
              where aufnr = <fs_mrp>-mrp_no12
                and lgort in s_lgort.

            if sy-subrc eq 0.
              gw_dtl-werks = werks.
              gw_dtl-matnr = matnr.
              gw_dtl-zdate = <fs_mrp>-avail_date."дата
              «Элементы ППМ
              select single delb0
                into gw_dtl-delb0
                from t457t
                where delkz = <fs_mrp>-mrp_element_ind
                  and spras = '1'.

              «Элементы данные ППМ
              if <fs_mrp>-peggedrqmt is initial.
                gw_dtl-extra = |{ <fs_mrp>-mrp_no }/{ <fs_mrp>-mrp_pos }|.
              else.
                gw_dtl-extra = <fs_mrp>-peggedrqmt.
              endif.

              "количество
              gw_dtl-mng01 = <fs_mrp>-rec_reqd_qty.
              append gw_dtl to alv.
            endif.

          when others.
        endcase.
      endloop.

    when 'ДА'."точка
      l_sundy = g_sundy.
      l_times = fname+3(2) - 1.
      do l_times times.
        l_mondy = l_sundy + 1.
        l_sundy = l_sundy + 7.
      enddo.

      if type = «А».»Поставка

        delete lt_mrp where ( avail_date gt l_sundy ) or ( avail_date lt l_mondy ).
        delete lt_mrp where plngsegno is not initial or plus_minus ne '+' or rec_reqd_qty is initial.

        loop at lt_mrp assigning <fs_mrp>.
          clear:gw_dtl.
          if <fs_mrp>-storage_loc in s_lgort.
            if <fs_mrp>-mrp_element_ind = 'PA' and <fs_mrp>-firmed ne 'X'.
              continue.
            else.
              gw_dtl-werks = werks.
              gw_dtl-matnr = matnr.
              gw_dtl-zdate = <fs_mrp>-avail_date."дата
              «Элементы ППМ
              select single delb0
                into gw_dtl-delb0
                from t457t
                where delkz = <fs_mrp>-mrp_element_ind
                  and spras = '1'.

              «Элементы данные ППМ
              if <fs_mrp>-peggedrqmt is initial.
                gw_dtl-extra = |{ <fs_mrp>-mrp_no }/{ <fs_mrp>-mrp_pos }|.
              else.
                gw_dtl-extra = <fs_mrp>-peggedrqmt.
              endif.

              "количество
              gw_dtl-mng01 = <fs_mrp>-rec_reqd_qty.
              append gw_dtl to alv.
            endif.
          endif.
        endloop.
      elseif type = «Б».»Требования
        delete lt_mrp where ( avail_date gt l_sundy ) or ( avail_date lt l_mondy ).
        delete lt_mrp where plngsegno is not initial or plus_minus ne '-' or rec_reqd_qty is initial.

        loop at lt_mrp assigning <fs_mrp>.
          clear:gw_dtl,l_lgort,l_auffx.
          case <fs_mrp>-order_type.
            when «ВВ».»Аутсорсинг закупок
              «Идите к столу ЭКПО, чтобы получить инвентарь, удовлетворяющий NO-X.
              select single lgort
                into l_lgort
                from ekpo
                where ebeln = <fs_mrp>-source_no
                  and ebelp = <fs_mrp>-source_item
                  and lgort in s_lgort.

              if sy-subrc eq 0.
                gw_dtl-werks = werks.
                gw_dtl-matnr = matnr.
                gw_dtl-zdate = <fs_mrp>-avail_date."дата
                «Элементы ППМ
                select single delb0
                  into gw_dtl-delb0
                  from t457t
                  where delkz = <fs_mrp>-mrp_element_ind
                    and spras = '1'.

                «Элементы данные ППМ
                if <fs_mrp>-peggedrqmt is initial.
                  gw_dtl-extra = |{ <fs_mrp>-mrp_no }/{ <fs_mrp>-mrp_pos }|.
                else.
                  gw_dtl-extra = <fs_mrp>-peggedrqmt.
                endif.

                "количество
                gw_dtl-mng01 = <fs_mrp>-rec_reqd_qty.
                append gw_dtl to alv.
              endif.

            when 'СБ'».Плановый заказ-нижний уровень
              «Перейдите к столу PLAF, чтобы получить инвентарь, соответствующий NO-X.
              select single lgort auffx
                into (l_lgort,l_auffx)
                from plaf
                where plnum = <fs_mrp>-source_no
                  and lgort in s_lgort.

              if sy-subrc eq 0.
                if l_auffx eq 'X'.
                  gw_dtl-werks = werks.
                  gw_dtl-matnr = matnr.
                  gw_dtl-zdate = <fs_mrp>-avail_date."дата
                  «Элементы ППМ
                  select single delb0
                    into gw_dtl-delb0
                    from t457t
                    where delkz = <fs_mrp>-mrp_element_ind
                      and spras = '1'.

                  «Элементы данные ППМ
                  if <fs_mrp>-peggedrqmt is initial.
                    gw_dtl-extra = |{ <fs_mrp>-mrp_no }/{ <fs_mrp>-mrp_pos }|.
                  else.
                    gw_dtl-extra = <fs_mrp>-peggedrqmt.
                  endif.

                  "количество
                  gw_dtl-mng01 = <fs_mrp>-rec_reqd_qty.
                  append gw_dtl to alv.
                endif.
              endif.

            when 'AR'."Резервирование производственного заказа
              «Перейдите к столу AFPO, чтобы получить инвентарь, соответствующий NO-X.
              select single lgort
                into l_lgort
                from afpo
                where aufnr = <fs_mrp>-mrp_no12
                  and lgort in s_lgort.

              if sy-subrc eq 0.
                gw_dtl-werks = werks.
                gw_dtl-matnr = matnr.
                gw_dtl-zdate = <fs_mrp>-avail_date."дата
                «Элементы ППМ
                select single delb0
                  into gw_dtl-delb0
                  from t457t
                  where delkz = <fs_mrp>-mrp_element_ind
                    and spras = '1'.

                «Элементы данные ППМ
                if <fs_mrp>-peggedrqmt is initial.
                  gw_dtl-extra = |{ <fs_mrp>-mrp_no }/{ <fs_mrp>-mrp_pos }|.
                else.
                  gw_dtl-extra = <fs_mrp>-peggedrqmt.
                endif.

                "количество
                gw_dtl-mng01 = <fs_mrp>-rec_reqd_qty.
                append gw_dtl to alv.
              endif.

            when others.
          endcase.
        endloop.
      endif.

    when others.

  endcase.

endform.                    "frm_get_detail

*&---------------------------------------------------------------------*
*&      Form  frm_get_text
*&---------------------------------------------------------------------*
*       Получить текст подсказки
*----------------------------------------------------------------------*
*      -->PERCENT    text
*      -->TEXT       text
*----------------------------------------------------------------------*
form frm_get_text using percent type i
                        text    type string.

  call function 'SAPGUI_PROGRESS_INDICATOR'
    exporting
      percentage = percent
      text       = text.

endform.                    "frm_get_text

*&---------------------------------------------------------------------*
*&      Form  frm_get_event
*&---------------------------------------------------------------------*
*       text
*----------------------------------------------------------------------*
form frm_get_event .
  data l_events type slis_alv_event."slis_alv_event — это структура, содержащая поля имени и формы, оба из которых являются символьными типами.

  call function 'REUSE_ALV_EVENTS_GET'
    exporting
      i_list_type     = 0
    importing
      et_events       = gt_events
    exceptions
      list_type_wrong = 1
      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.

endform.                    "frm_get_event

*&---------------------------------------------------------------------*
*&      Form  frm_sort_build
*&---------------------------------------------------------------------*
*       Настройки сортировки вывода
*----------------------------------------------------------------------*
*      -->LT_SORT    text
*----------------------------------------------------------------------*
form frm_sort_build changing lt_sort type slis_t_sortinfo_alv.
  data: ls_sort type slis_sortinfo_alv.
  refresh lt_sort.

  clear ls_sort.
  ls_sort-spos = 1.
  ls_sort-fieldname = 'WERKS'.
  ls_sort-up   = 'X'.
  append ls_sort to lt_sort.

  clear ls_sort.
  ls_sort-spos = 2.
  ls_sort-fieldname = 'DISPO'.
  ls_sort-up   = 'X'.
  append ls_sort to lt_sort.

  clear ls_sort.
  ls_sort-spos = 3.
  ls_sort-fieldname = 'MATNR'.
  ls_sort-up   = 'X'.
  append ls_sort to lt_sort.

  clear ls_sort.
  ls_sort-spos = 4.
  ls_sort-fieldname = 'MEINS'.
  ls_sort-up   = 'X'.
  append ls_sort to lt_sort.

  clear ls_sort.
  ls_sort-spos = 5.
  ls_sort-fieldname = 'MAKTX'.
  ls_sort-up   = 'X'.
  append ls_sort to lt_sort.

endform.                    "frm_sort_build

*&---------------------------------------------------------------------*
*&      Form  frm_init_layout
*&---------------------------------------------------------------------*
*       настройки макета
*----------------------------------------------------------------------*
form frm_init_layout.
  gw_layout-zebra  = 'X'».Изменение цвета интервальной строки
  gw_layout-detail_popup = 'X'.
  gw_layout-colwidth_optimize = 'X'.»Автоматическая регулировка ширины столбцов

endform.                    " FRM_INIT_LAYOUT

*&---------------------------------------------------------------------*
*&      Form  frm_fcat_setting
*&---------------------------------------------------------------------*
*       Установить поля вывода
*----------------------------------------------------------------------*
form frm_fcat_setting.
  data: l_num type n length 2,
        l_txt type c length 20, «Поле
        l_dis type c length 20, «Описание
        l_mondy type d,
        l_sundy type d.
  refresh gt_fieldcat.

  perform frm_init_fieldcat using 'WERKS' 'фабрика'           'X' 'X' ' ' ' ' ' '.
  perform frm_init_fieldcat using 'DISPO' «Контроллер MRP»      'X' 'X' ' ' ' ' ' '.
  perform frm_init_fieldcat using 'MATNR' «Номер материала»         'X' 'X' ' ' 'X' ' '.
  perform frm_init_fieldcat using 'MEINS' 'единица'           'X' 'X' ' ' ' ' ' '.
  perform frm_init_fieldcat using 'MAKTX' «Описание материала»       'X' 'X' ' ' ' ' ' '.
  perform frm_init_fieldcat using 'LABST' 'NO-Xнеограниченный инвентарь' 'X' 'X' ' ' 'X' ' '.
  perform frm_init_fieldcat using 'ZSUPL' 'NO-XПросроченный запас'   'X' 'X' 'X' 'X' ' '.
  perform frm_init_fieldcat using 'ZREQD' 'NO-XПросроченные требования'   'X' 'X' 'X' 'X' ' '.
  perform frm_init_fieldcat using 'ZTEXT' 'период'           'X' 'X' ' ' ' ' ' '.
  «Поле периода динамического вывода
  clear:l_num,l_txt,l_dis.
  l_mondy = g_mondy.
  l_sundy = g_sundy.
  do 12 times.
    l_num = l_num + 1.
    l_txt = |DAT{ l_num }|.
    l_dis = |{ l_mondy }-{ l_sundy }|.
    perform frm_init_fieldcat using l_txt l_dis ' ' ' ' 'X' 'X' ' '.
    l_mondy = l_sundy + 1.
    l_sundy = l_sundy + 7.
  enddo.

endform.                    "frm_fcat_setting

*&---------------------------------------------------------------------*
*&      Form  frm_init_fieldcat
*&---------------------------------------------------------------------*
*      инициализация выходного поля
*----------------------------------------------------------------------*
*      -->VALU01     text
*      -->VALU02     text
*      -->VALU03     text
*      -->VALU04     text
*      -->VALU05     text
*      -->VALU06     text
*      -->VALU07     text
*----------------------------------------------------------------------*
form frm_init_fieldcat using valu01
                             valu02
                             valu03
                             valu04
                             valu05
                             valu06
                             valu07.

  clear:gt_fieldcat.
  gt_fieldcat-fieldname  = valu01."Имя поля
  gt_fieldcat-seltext_m  = valu02."Описание поля
  gt_fieldcat-key        = valu03."Первичный ключ
  gt_fieldcat-fix_column = valu04."Фиксированный столбец
  gt_fieldcat-hotspot    = valu05."горячая точка
  gt_fieldcat-no_zero    = valu06."Скрыть ведущие нули
  gt_fieldcat-no_sign    = значение07." символ
  append gt_fieldcat.

endform.                    "frm_set_fcat


*&---------------------------------------------------------------------*
*&      Form  frm_output
*&---------------------------------------------------------------------*
*       text
*----------------------------------------------------------------------*
*      -->TAB        text
*----------------------------------------------------------------------*
form frm_output tables tab.
*Выход АЛВ
  g_repid = sy-repid.

  call function 'REUSE_ALV_GRID_DISPLAY'
    exporting
      i_callback_program      = g_repid
      is_layout               = gw_layout
      it_fieldcat             = gt_fieldcat[]
      i_save                  = 'X'
      is_variant              = gw_stru_disvar» информация о переменной
      it_events               = gt_events[]
      it_sort                 = gt_sort[]
      i_callback_user_command = 'FRM_USER_COMMAND'
    tables
      t_outtab                = tab
    exceptions
      program_error           = 1
      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.
endform.                    "frm_output

*&---------------------------------------------------------------------*
*&      Form  FRM_USER_COMMAND
*&---------------------------------------------------------------------*
*       событие处理
*----------------------------------------------------------------------*
*      -->R_UCOMM      text
*      -->RS_SELFIELD  text
*----------------------------------------------------------------------*
form frm_user_command using r_ucomm like sy-ucomm
                            rs_selfield type slis_selfield.

  clear:gt_dtl.
  case r_ucomm.
    when '&IC1'.
      read table gt_out assigning <fs_out> index rs_selfield-tabindex.
      if rs_selfield-fieldname = 'ZSUPL' or rs_selfield-fieldname = «ZREQD».»Спрос/предложение
        perform frm_get_detail tables gt_dtl
                               using <fs_out>-matnr
                                     <fs_out>-werks
                                     rs_selfield-fieldname
                                     <fs_out>-ztype.

        if gt_dtl is not initial.
          call screen 0100 starting at 30 5.
        endif.
      else.
        if rs_selfield-fieldname+0(3) = 'DAT'.
          perform frm_get_detail tables gt_dtl
                                 using <fs_out>-matnr
                                       <fs_out>-werks
                                       rs_selfield-fieldname
                                       <fs_out>-ztype.

          if gt_dtl is not initial.
            call screen 0100 starting at 30 5.
          endif.
        endif.
      endif.

    when others.
  endcase.
endform.                    "FRM_USER_COMMAND

*&---------------------------------------------------------------------*
*&      Form  frm_set_fcat
*&---------------------------------------------------------------------*
*       Настройки поля вывода
*----------------------------------------------------------------------*
form frm_set_fcat.
  if gt_fcat is initial.
    clear: gw_fcat.
    gw_fcat-col_pos    = 1.
    gw_fcat-fieldname  = 'WERKS'.
    gw_fcat-tabname    = 'MARC'.
    gw_fcat-scrtext_m  = 'фабрика'.
    append gw_fcat to gt_fcat.

    clear: gw_fcat.
    gw_fcat-col_pos    = 2.
    gw_fcat-fieldname  = 'MATNR'.
    gw_fcat-tabname    = 'MARC'.
    gw_fcat-scrtext_m  = «материалы».
    gw_fcat-no_zero    = 'X'.
    append gw_fcat to gt_fcat.

    clear: gw_fcat.
    gw_fcat-col_pos    = 3.
    gw_fcat-fieldname  = 'ZDATE'.
    gw_fcat-scrtext_m  = 'дата'.
    append gw_fcat to gt_fcat.

    clear: gw_fcat.
    gw_fcat-col_pos    = 4.
    gw_fcat-fieldname  = 'DELB0'.
    gw_fcat-tabname    = 'T457T'.
    gw_fcat-scrtext_m  = «Элемент ППМ».
    append gw_fcat to gt_fcat.

    clear: gw_fcat.
    gw_fcat-col_pos    = 5.
    gw_fcat-fieldname  = 'EXTRA'.
    gw_fcat-tabname    = 'MDEZ'.
    gw_fcat-scrtext_m  = «Данные элемента ППМ».
    gw_fcat-fix_column = 'X'.
    append gw_fcat to gt_fcat.

    clear: gw_fcat.
    gw_fcat-col_pos    = 6.
    gw_fcat-fieldname  = 'MNG01'.
    gw_fcat-tabname    = 'MDEZ'.
    gw_fcat-scrtext_m  = «Полученное количество или требуемое количество».
    gw_fcat-fix_column = 'X'.
    gw_fcat-do_sum     = 'X'.
    append gw_fcat to gt_fcat.
  endif.
endform.                    "frm_set_fcat

*&---------------------------------------------------------------------*
*&      Form  frm_set_lock
*&---------------------------------------------------------------------*
*       Заблокировано
*----------------------------------------------------------------------*
form frm_set_lock.
  «Блокировка программы
  call function 'ENQUEUE_EZZSOPR0032'
    exporting
      mode_trdir     = 'E'
      name           = 'ZPPR0056'
      x_name         = ' '
      _scope         = '2'
      _wait          = ' '
      _collect       = ' '
    exceptions
      foreign_lock   = 1
      system_failure = 2
      others         = 3.

  if sy-subrc <> 0.
* Implement suitable error handling here
    message «Объект заблокирован, выполните позже» type 'S' display like 'E'.
    stop.
  else.
    «Блокировка успешна
  endif.
endform.                    "frm_set_lock

*&---------------------------------------------------------------------*
*&      Form  frm_set_unlock
*&---------------------------------------------------------------------*
*       Разблокировать
*----------------------------------------------------------------------*
form frm_set_unlock.
  «Разблокировать программу
  call function 'DEQUEUE_EZZSOPR0032'
    exporting
      mode_trdir = 'E'
      name       = 'ZPPR0056'
      x_name     = ' '
      _scope     = '3'
      _synchron  = ' '
      _collect   = ' '.
endform.                    "frm_set_unlock

*&---------------------------------------------------------------------*
*&      Module  STATUS_0100  OUTPUT
*&---------------------------------------------------------------------*
*       text
*----------------------------------------------------------------------*
module status_0100 output.
  set pf-status 'ZSTA1'.
*  SET TITLEBAR 'xxx'.
  create object g_alv.
  g_alv->main( ).
endmodule.                 " STATUS_0100  OUTPUT

*&---------------------------------------------------------------------*
*&      Module  EXIT  INPUT
*&---------------------------------------------------------------------*
*       text
*----------------------------------------------------------------------*
module exit input.
  leave to screen 0.

endmodule.                 " EXIT  INPUT
boy illustration
Учебное пособие по Jetpack Compose для начинающих, базовые элементы управления и макет
boy illustration
Код js веб-страницы, фон частицы, код спецэффектов
boy illustration
【новый! Суперподробное】Полное руководство по свойствам компонентов Figma.
boy illustration
🎉Обязательно к прочтению новичкам: полное руководство по написанию мини-программ WeChat с использованием программного обеспечения Cursor.
boy illustration
[Забавный проект Docker] VoceChat — еще одно приложение для мгновенного чата (IM)! Может быть встроен в любую веб-страницу!
boy illustration
Как реализовать переход по странице в HTML (html переходит на указанную страницу)
boy illustration
Как решить проблему зависания и низкой скорости при установке зависимостей с помощью npm. Существуют ли доступные источники npm, которые могут решить эту проблему?
boy illustration
Серия From Zero to Fun: Uni-App WeChat Payment Practice WeChat авторизует вход в систему и украшает страницу заказа, создает интерфейс заказа и инициирует запрос заказа
boy illustration
Серия uni-app: uni.navigateЧтобы передать скачок значения
boy illustration
Апплет WeChat настраивает верхнюю панель навигации и адаптируется к различным моделям.
boy illustration
JS-время конвертации
boy illustration
Обеспечьте бесперебойную работу ChromeDriver 125: советы по решению проблемы chromedriver.exe не найдены
boy illustration
Поле комментария, щелчок мышью, специальные эффекты, js-код
boy illustration
Объект массива перемещения объекта JS
boy illustration
Как открыть разрешение на позиционирование апплета WeChat_Как использовать WeChat для определения местонахождения друзей
boy illustration
Я даю вам два набора из 18 простых в использовании фонов холста Power BI, так что вам больше не придется возиться с цветами!
boy illustration
Получить текущее время в js_Как динамически отображать дату и время в js
boy illustration
Вам необходимо изучить сочетания клавиш vsCode для форматирования и организации кода, чтобы вам больше не приходилось настраивать формат вручную.
boy illustration
У ChatGPT большое обновление. Всего за 45 минут пресс-конференция показывает, что OpenAI сделал еще один шаг вперед.
boy illustration
Copilot облачной разработки — упрощение разработки
boy illustration
Микросборка xChatGPT с низким кодом, создание апплета чат-бота с искусственным интеллектом за пять шагов
boy illustration
CUDA Out of Memory: идеальное решение проблемы нехватки памяти CUDA
boy illustration
Анализ кластеризации отдельных ячеек, который должен освоить каждый&MarkerгенетическийВизуализация
boy illustration
vLLM: мощный инструмент для ускорения вывода ИИ
boy illustration
CodeGeeX: мощный инструмент генерации кода искусственного интеллекта, который можно использовать бесплатно в дополнение к второму пилоту.
boy illustration
Машинное обучение Реальный бой LightGBM + настройка параметров случайного поиска: точность 96,67%
boy illustration
Бесшовная интеграция, мгновенный интеллект [1]: платформа больших моделей Dify-LLM, интеграция без кодирования и встраивание в сторонние системы, более 42 тысяч звезд, чтобы стать свидетелями эксклюзивных интеллектуальных решений.
boy illustration
LM Studio для создания локальных больших моделей
boy illustration
Как определить количество слоев и нейронов скрытых слоев нейронной сети?
boy illustration
[Отслеживание целей] Подробное объяснение ByteTrack и детали кода