Что, если я не использую индексные поля в своей программе?

#openedge #progress-4gl

#openedge #прогресс -4gl

Вопрос:

Я новичок в этом progress 4GL. Я запутался в следующей логике, особенно в том, как на самом деле работает индекс.

Я добавил 2 поля в один индекс. Как вы можете видеть ниже, я написал три запроса.

Запрос 1, использовал индекс и поиск данных из 2 полей для извлечения данных

Запрос 2, использовал тот же индекс, но находил данные только из 1 поля

В запросе 3 использовалось то же индексное поле с одним неиндексным полем

 define temp-table tt_creldata no-undo
field tt_cscx_order    as character 
field tt_cscx_part     as character
field tt_cscx_shipfrom as character
index tt_cscx
      tt_cscx_order
      tt_cscx_part
.
**Query 1:**
find first tt_creldata use-index tt_cscx 
      where tt_cscx_order = "153" 
      and tt_cscx_part = "113" no-lock no-error.

**Query 2:**
find first tt_creldata use-index tt_cscx 
       where tt_cscx_order = "153" no-lock no-error.

**Query 3:**
find first tt_creldata use-index tt_cscx
      where tt_cscx_order = "153" 
      and tt_cscx_part = "113" 
      and tt_cscx_shipfrom = "US" no-lock no-error.
 

Вопрос 1. Какой запрос помогает повысить производительность

Вопрос 2: Что, если я не использую одно поле, которое индексируется, когда я упомянул use-index

Вопрос 3. Что, если я добавлю одно неиндексное поле, когда я упомянул use-index?

Ответ №1:

Как общее эмпирическое правило, вы никогда не должны использовать use-index .

AVM выберет один или несколько индексов для использования в запросе во время компиляции, и, заставляя его использовать один из выбранных вами, вы устраняете возможность этого.

Наличие дополнительных, возможно, неиндексных полей в вашем предложении where повлияет на выбранные индексы только в том случае, если вы позволите AVM выбрать (т. Е. Не использовать use-index ). Это также верно, если вы не используете индексированные поля в своем запросе.

Вы можете увидеть, какие индексы используются, если скомпилируете программу с параметрами xref или xml-xref и выполните поиск SEARCH элементов.

Ответ №2:

Как говорит нвахмает, вы никогда не должны использовать USE-INDEX . В этом случае это особенно бессмысленно, потому что существует только один индекс. В случаях, когда имеется несколько индексов, оператор FIND будет использовать только один из них, независимо от того, насколько сложным является предложение WHERE, но компилятор почти всегда справится с выбором эффективного индекса лучше, чем вы. (Оператор FOR EACH и связанные с ним динамические запросы могут использовать несколько индексов. ПОИСК всегда ограничен только одним индексом.) В тех редких случаях, когда вы считаете, что выполняете работу лучше, вы должны тщательно документировать, почему ваш выбор лучше, и включать подробные тестовые примеры и результаты.

Все ваши запросы используются в ПЕРВУЮ ОЧЕРЕДЬ. Это необходимо, потому что ваш индекс не определен как уникальный. Это может быть вашим намерением, но это кажется необычным. И это означает, что в случае дублирования записей с одинаковыми значениями ключей вы волшебным образом делаете «первую» запись более особенной, чем остальные. Что является ошибкой нормализации данных (вы делаете «первичность» атрибутом данных) и ожидающей появления ошибки.

FIND FIRST и USE-INDEX часто используются вместе, чтобы (попытаться) скрыть недостатки друг друга. При указании определенного индекса ПЕРВЫЙ становится более согласованным. Аналогично, FIRST часто используется для «устранения» проблем с производительностью, возникающих из-за недостаточных определений индексов, неадекватных предложений WHERE или выбора FIND when ДЛЯ КАЖДОГО было бы более подходящим.

Ни один из этих запросов не будет выполняться заметно быстрее, чем другие.

Запрос 2 может возвращать или не возвращать ту же запись, что и запрос 1. Например, если есть part = «112», то запрос 2 будет иметь другую «первую» запись. Но возврат будет таким же быстрым, как и запрос 1.

Аналогично, запрос 3 может иметь другой результат в зависимости от того, какие записи содержат shipfrom = «US» . В лучшем случае, когда самый первый порядок = «153» и часть «113» также удовлетворяют shipfrom = «US», тогда это будет та же скорость, что и у других.

Однако запрос 3 может быть намного медленнее в зависимости от того, сколько записей нужно отсканировать, прежде чем будет найдена запись с shipfrom = «US», поскольку это поле не является частью какого-либо индекса, и поэтому для его сопоставления потребуется сканировать записи, пока не будет найдена соответствующая. Это может быть первая запись или 10-миллионная.