Поиск в массиве данных RPGLE

Я создал массив структур данных, и я хочу посмотреть на основе комбинации клавиш. то есть в приведенном ниже DS я хочу найти и получить индекс, если tblName и tblElement и tblDivision совпадают, а затем вернуть значение tblRes.

    D TblAryDs        DS                  qualified dim(9999)                    
    D  tblName                       3                                           
    D  tblElement                   10                                           
    D  tblDivision                   5                                           
    D  tblRes                        2                                           

//Not Sure How to do the below lookup
      idx = %lookup(tblName:TblAryDs(*).tblName) && %lookup(tblElement:TblAryDs(*).tblElement) && %lookup(tblDivision:TblAryDs(*).tblDivision);                                
      if idx > *zeros;                                                                                   
         return TblAryDs(*).tblRes;
      endif; 

person Sekar    schedule 22.03.2017    source источник


Ответы (1)


 D TblAryDs        DS                  qualified dim(9999)                    
 D  key
 D    tblName                     3a   overlay(key)                                        
 D    tblElement                 10a   overlay(key:*next)                                        
 D    tblDivision                 5a   overlay(key:*next)                                        
 D  tblRes                        2a           

  /FREE
    idx = %lookup(tblName + tblElement + tblDivision 
                  :TblAryDs(*).key); 
    if idx > *ZEROS;
      return TblAryDs(idx).tblRes;
    endif; 
  /END-FREE  

Примечание: как указано выше, %LOOKUP() будет искать все 9999 элементов. Если вам приходится многократно искать разные значения, добавьте в массив ключевое слово ASCEND и используйте SORTA для его сортировки перед поиском. Наконец, следите за тем, сколько элементов фактически используется в массиве.

idx = %lookup(tblName + tblElement + tblDivision 
                  : TblAryDs(*).key : nbrElemUsed);

Таким образом, %LOOKUP()% будет выполнять гораздо более быстрый двоичный поиск только активных элементов.

person Charles    schedule 22.03.2017
comment
Если в моем массиве есть следующие элементы, BIL-123-123-11 и BIL-456-456-22, и мне нужно найти строку отправки, этот код не будет работать. Поскольку поиск всегда возвращает первую строку. - person Sekar; 22.03.2017
comment
@Sekar Извините, неправильно понял, что вам нужно. Как насчет сейчас? - person Charles; 22.03.2017
comment
Это решает проблему. Спасибо. Один вопрос, хотя, поскольку я буду добавлять элементы во время выполнения, сортировка массива после добавления каждого элемента займет много времени. Фактический сценарий заключается в том, что вместо того, чтобы просматривать файл каждый раз, когда я хочу максимально кэшировать результаты, чтобы уменьшить количество операций ввода-вывода. Очень хотелось бы узнать ваше мнение по этому поводу. Будет ли сортировка и поиск занимать много времени или файловый ввод-вывод? - person Sekar; 22.03.2017
comment
Файловый ввод-вывод более затратен, но не так сильно, как вы могли бы подумать, из-за природы одноуровневого хранилища. На самом деле вы не будете нажимать на диск для каждого ввода-вывода. SETOBJACC даже позволит вам предварительно загрузить весь файл в память. Через БД все еще остаются некоторые накладные расходы... но если преждевременная оптимизация действительно является корнем всех зол Я бы начал с простого и просто выполнял файловый ввод-вывод. Затем перейдите к указанию системе кэшировать его, прежде чем создавать собственное кэширование. - person Charles; 22.03.2017
comment
В противном случае, если бы я построил собственное кэширование, я бы посмотрел на загрузку всего этого, а затем на сортировку. Проблема в том, нужно ли вам беспокоиться об изменении данных в файле, что сделает ваш кеш или он устарел? - person Charles; 22.03.2017