AXForum  
Вернуться   AXForum > Microsoft Dynamics AX > DAX: Программирование
All
Забыли пароль?
Зарегистрироваться Правила Справка Пользователи Сообщения за день Поиск

 
 
Опции темы Поиск в этой теме Опции просмотра
Старый 30.07.2009, 17:17   #1  
S.Kuskov is offline
S.Kuskov
Участник
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
 
3,438 / 1775 (66) ++++++++
Регистрация: 28.04.2007
Адрес: Калуга
Зачем нужен уникальный index, содержащий RecId?
На некотроых таблицах уровня SYS наблюдается наличие уникального индекса в состав, которого по мимо прочих полей входит поле RecId (например индекс ItemIdx на таблице InventItemBarcode). Известно что если не включать RecId в индекс и не делать его уникальным, то система по умолчанию на уровне БД сама создаст его (Проблема с индексами).

Отсюда вопрос. Какой смысл вручную создавать такой абсурдный с точки зрения приложения индекс (уникальность RecId - это всё же забота ядра и БД). И не в этом ли кроются ошибки, такие как Существуют аргументы, почему неуникальность баркода у номенклатуры не является багой?

Т.е. на мой взгляд, уникальные индексы необходимы для ограничения дубликатов строк, а какой в них толк, если они содержат поле RecID, уникальное априори? Следовательно либо требование уникальности здесь избыточно, либо наличие в уникальном индексе поля RecId является ошибкой проектирования, вызванной попыткой уменьшить число индексов на таблице.
Старый 30.07.2009, 17:33   #2  
ZVV is offline
ZVV
MCITP
MCP
Oracle
MCBMSS
 
1,006 / 246 (11) ++++++
Регистрация: 13.02.2004
Адрес: Минск
->
Цитата:
Сообщение от S.Kuskov Посмотреть сообщение
На некотроых таблицах уровня SYS наблюдается наличие уникального индекса в состав, которого по мимо прочих полей входит поле RecId (например индекс ItemIdx на таблице InventItemBarcode). Известно что если не включать RecId в индекс и не делать его уникальным, то система по умолчанию на уровне БД сама создаст его (Проблема с индексами).

Отсюда вопрос. Какой смысл вручную создавать такой абсурдный с точки зрения приложения индекс (уникальность RecId - это всё же забота ядра и БД). И не в этом ли кроются ошибки, такие как Существуют аргументы, почему неуникальность баркода у номенклатуры не является багой?

Т.е. на мой взгляд, уникальные индексы необходимы для ограничения дубликатов строк, а какой в них толк, если они содержат поле RecID, уникальное априори? Следовательно либо требование уникальности здесь избыточно, либо наличие в уникальном индексе поля RecId является ошибкой проектирования, вызванной попыткой уменьшить число индексов на таблице.

Вы же сами ответили на свой вопрос...
Здесь уже писал об алгоритме: Не выделять RecId

Т.е. это добавление идёт только в случае когда в таблице нет вообще индексов уникальных.. А уникальный индекс Аксапте нужен...

Например для работы .reread()...
__________________
Zhirenkov Vitaly
Старый 30.07.2009, 17:47   #3  
fed is offline
fed
Moderator
Аватар для fed
Ex AND Project
Соотечественники
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
Лучший по профессии AXAWARD 2013
Лучший по профессии 2011
Лучший по профессии 2009
 
2,907 / 5717 (196) ++++++++++
Регистрация: 13.03.2002
Адрес: Hüfingen,DE
К слову сказать - для производительности SQL-сервера (и MS SQL и Oracle) выгоднее индексы с более высокой селективностью (в идеале - уникальные). В тех случаях, когда системе нужно по значению клуча найти нужную запись в индексе (например - при удалении записи в таблице), система, в первом приближении, перебирает все записи с данным ключем, до тех пор пока не найдет ту запись у которой физический адрес записи в таблице совпадает с необходимым. Поэтому если у таблицы много неуникальных индексов с малой селективностью (порядка сотен записей с одинаковым ключем), обновление начинает подтормаживать. В таких случаях можно довольно заметно ускорить работу с таблицей, преобразовав часть подобных индексов в уникальные. Некоторое увеличение индекса и времени поиска по индексу из за хранения лишнего поля, с лихвой компенсируется заметным уменьшением времени обновления.
Ну и как уже написали предыдущие ораторы - для работы системы кэширования аксаптовской, система должна иметь хотя бы один уникальный индекс.
Старый 30.07.2009, 17:51   #4  
ZVV is offline
ZVV
MCITP
MCP
Oracle
MCBMSS
 
1,006 / 246 (11) ++++++
Регистрация: 13.02.2004
Адрес: Минск
->
Цитата:
Сообщение от fed Посмотреть сообщение
В тех случаях, когда системе нужно по значению клуча найти нужную запись в индексе (например - при удалении записи в таблице), система, в первом приближении, перебирает все записи с данным ключем, до тех пор пока не найдет ту запись у которой физический адрес записи в таблице совпадает с необходимым. Поэтому если у таблицы много неуникальных индексов с малой селективностью (порядка сотен записей с одинаковым ключем), обновление начинает подтормаживать.
Аксапта, насколько я знаю, так не работает (перебирает неуникальные индексы) по указанной выше причине - всегда есть уникальный индекс и она его использует. В частности да, при выполнении .update() или .delete(), в чём можно убедиться, включив лог операторов SQL.

Или это было о том как теоретически могло бы быть?
__________________
Zhirenkov Vitaly
Старый 30.07.2009, 18:23   #5  
belugin is offline
belugin
Участник
Аватар для belugin
Сотрудники Microsoft Dynamics
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
Лучший по профессии 2011
Лучший по профессии 2009
 
4,622 / 2925 (107) +++++++++
Регистрация: 16.01.2004
Записей в блоге: 5
Еще есть такой прием (в одной книжке по ораклу вычитал) как overindexing - в индекс добавляется поле, которое нужно выбирать при выборке по индексу. Таким образом не нужна операция по подъему из базы страниц с данными - значение берется из индекса.

то есть если будет запрос

X++:
select recID from T where T.ItemID = 'z'
то будет выбрана одна страница с индексом, а не сначала страница с индексом, а потом с страница с данными самой таблицы.
Старый 30.07.2009, 18:34   #6  
ZVV is offline
ZVV
MCITP
MCP
Oracle
MCBMSS
 
1,006 / 246 (11) ++++++
Регистрация: 13.02.2004
Адрес: Минск
->
Цитата:
Сообщение от belugin Посмотреть сообщение
Еще есть такой прием (в одной книжке по ораклу вычитал) как overindexing - в индекс добавляется поле, которое нужно выбирать при выборке по индексу. Таким образом не нужна операция по подъему из базы страниц с данными - значение берется из индекса.

то есть если будет запрос

X++:
select recID from T where T.ItemID = 'z'
то будет выбрана одна страница с индексом, а не сначала страница с индексом, а потом с страница с данными самой таблицы.
Первый раз слышу такой термин, если честно...
Но подход да, стар как мир - оптимизатор позволяет исключить обращение к таблице, если все данные есть в индексе.

Кстати в SQL2005 есть новая фича, называется "Included columns", тоже на эту тему... Правда вот Аксапте это вряд ли поможет
__________________
Zhirenkov Vitaly
Старый 30.07.2009, 18:47   #7  
belugin is offline
belugin
Участник
Аватар для belugin
Сотрудники Microsoft Dynamics
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
Лучший по профессии 2011
Лучший по профессии 2009
 
4,622 / 2925 (107) +++++++++
Регистрация: 16.01.2004
Записей в блоге: 5
Цитата:
Сообщение от ZVV Посмотреть сообщение
Первый раз слышу такой термин, если честно...
может и напутал.
Старый 30.07.2009, 18:53   #8  
fed is offline
fed
Moderator
Аватар для fed
Ex AND Project
Соотечественники
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
Лучший по профессии AXAWARD 2013
Лучший по профессии 2011
Лучший по профессии 2009
 
2,907 / 5717 (196) ++++++++++
Регистрация: 13.03.2002
Адрес: Hüfingen,DE
Цитата:
Сообщение от ZVV Посмотреть сообщение
Аксапта, насколько я знаю, так не работает (перебирает неуникальные индексы) по указанной выше причине - всегда есть уникальный индекс и она его использует. В частности да, при выполнении .update() или .delete(), в чём можно убедиться, включив лог операторов SQL.

Или это было о том как теоретически могло бы быть?
А это вообще не на аксаптовском уровне происходит. И даже не на уровне трейсинга SQL-операторов в SQL Profiler. Вот представь себе: У тебя есть таблица персонала. Есть куча индексов, один из которых по полю Пол. Ты говоришь - удалить сотрудника с employeeId=='Иванов И.И.'. Система находит по индексу emplIdIdx физический адрес записи и фетчит ее. Далее - надо удалить из всех индексов ключи, которые на эту запись ссылаются. Система рассчитывает значения индексных ключей (по данным из записи) и пытается найти и удалить все индексные ключи. Для этого она ПЕРЕБИРАЕТ все индексные ключи со значением равным вычисленному до тех пор, пока не наткнется на ключ, ссылающийся на нужную запись (то есть с сохраненным в индексном входе Row_Id==Row_ID нашей записи). Если индекс уникален, то этот перебор не требуется. Если относительно уникален (ну скажем - номер паспорта без серии) - то перебор будет недолгим. А вот если это индекс по полю типа Пол (два возможных значения) - перебор будет медленным и печальным. Собственно - по этому в книжках и не советуют строить индексы по полям с 2-5-10 возможными значениями - обновление такой индекс затормозит, а при выборке редко будет нужен. Но тем не менее - иногда приходится строить индексы по достаточно часто повторяющемуся полю. Даже если на каждое значение будет приходиться порядка 200-300 записей - все равно обновление тормозить будет изрядно.

Насколько я знаю - некоторые БД пытались решить эту проблему за счет того, что индекс подспудно сортировался по сочетанию ключ+физический адрес записи (ROW_ID). (То есть - значение ссылки на запись становилась некой виртуальной частью ключа). Однако - на практике это приводило к изрядным проблемам, поскольку приводило к усиленной перебалансировке дерева страниц при вставке новых записей. Кроме того - при реорганизации и упаковке таблиц, это усложняло перестроение индексов.
Так что - насколько я понимаю, в текущих версиях и SQL Server и Oracle используется именно такой подход к удалению ключей, который я описал...
За это сообщение автора поблагодарили: Logger (1), Kabardian (4).
Старый 30.07.2009, 19:01   #9  
S.Kuskov is offline
S.Kuskov
Участник
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
 
3,438 / 1775 (66) ++++++++
Регистрация: 28.04.2007
Адрес: Калуга
Цитата:
Сообщение от ZVV Посмотреть сообщение
Т.е. это добавление идёт только в случае когда в таблице нет вообще индексов уникальных.. А уникальный индекс Аксапте нужен...
Возможно я что-то путаю, но разве авотматическое добаление RecId в индекс не ограничивается лишь уровенем БД? В смысле меняется ли автоматически индекс и в самом приложении (АОТ)? Если меняется, то в какой момент? при сохранении таблицы? при синхронизации?
Старый 30.07.2009, 19:12   #10  
S.Kuskov is offline
S.Kuskov
Участник
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
 
3,438 / 1775 (66) ++++++++
Регистрация: 28.04.2007
Адрес: Калуга
И ещё возник такой вопрос. Если уникальность RecId контролируется составным индексом, где помимо RecId присутствуют ещё и другие поля, то уникальность отдельно самого поля RecId, вообще говоря, уже не обеспечивается. Не является ли это потенциальным источником ошибок?
Старый 30.07.2009, 20:42   #11  
Андре is offline
Андре
Moderator
Сотрудники компании GMCS
 
2,375 / 464 (20) +++++++
Регистрация: 03.12.2001
Цитата:
Насколько я знаю - некоторые БД пытались решить эту проблему за счет того, что индекс подспудно сортировался по сочетанию ключ+физический адрес записи (ROW_ID). (То есть - значение ссылки на запись становилась некой виртуальной частью ключа). Однако - на практике это приводило к изрядным проблемам, поскольку приводило к усиленной перебалансировке дерева страниц при вставке новых записей. Кроме того - при реорганизации и упаковке таблиц, это усложняло перестроение индексов.
Так что - насколько я понимаю, в текущих версиях и SQL Server и Oracle используется именно такой подход к удалению ключей, который я описал...
Насколько я помню, Oracle в таких случаях предлагает использовать bitmap-индексы (индексы на основе битовых карт - не уверен в переводе), которые по своей сути не являются деревьями и решают обозначенную тобой проблему.

Правда для того, чтобы Аксапта создавала такие индексы ее придется слегка допилить.
Старый 30.07.2009, 20:45   #12  
Андре is offline
Андре
Moderator
Сотрудники компании GMCS
 
2,375 / 464 (20) +++++++
Регистрация: 03.12.2001
Цитата:
Еще есть такой прием (в одной книжке по ораклу вычитал) как overindexing - в индекс добавляется поле, которое нужно выбирать при выборке по индексу.
Покрывающий индекс - кажется так это называется. Индекс, которого достаточно для получения результатирующего набора данных без обращения к таблице.
Старый 30.07.2009, 21:00   #13  
ZVV is offline
ZVV
MCITP
MCP
Oracle
MCBMSS
 
1,006 / 246 (11) ++++++
Регистрация: 13.02.2004
Адрес: Минск
->
petr, fed -- теперь я понял о чём вы, это всё понятно и верно, но непонятно какое отношение к исходному вопросу?
__________________
Zhirenkov Vitaly
Старый 30.07.2009, 21:11   #14  
ZVV is offline
ZVV
MCITP
MCP
Oracle
MCBMSS
 
1,006 / 246 (11) ++++++
Регистрация: 13.02.2004
Адрес: Минск
->
Цитата:
Сообщение от S.Kuskov Посмотреть сообщение
Возможно я что-то путаю, но разве авотматическое добаление RecId в индекс не ограничивается лишь уровенем БД? В смысле меняется ли автоматически индекс и в самом приложении (АОТ)? Если меняется, то в какой момент? при сохранении таблицы? при синхронизации?
не путаете, в Аот - не сохраняет, тем не менее где-то запоминает...
можете попробовать сами: на таблице с индексом по Field1 (неуникальным) в случае .update() на БД уйдёт запрос вида:
X++:
UPDATE TABLE2 SET FIELD1=?,RECVERSION=? WHERE ((((DATAAREAID=?) AND (FIELD1=?)) AND (RECID=?)) AND (RECVERSION=?))
Цитата:
Сообщение от S.Kuskov Посмотреть сообщение
И ещё возник такой вопрос. Если уникальность RecId контролируется составным индексом, где помимо RecId присутствуют ещё и другие поля, то уникальность отдельно самого поля RecId, вообще говоря, уже не обеспечивается. Не является ли это потенциальным источником ошибок?
Нет, не контролируется. Более того есть море таблиц с уникальными ключами на них, и для которых RecId нет в принципе ни в каких индексах. Но это тема для отдельного разговора, много раз всплывало на форуме...
__________________
Zhirenkov Vitaly
Старый 30.07.2009, 21:19   #15  
SRF is offline
SRF
Участник
MCBMSS
Axapta Retail User
 
375 / 562 (19) +++++++
Регистрация: 08.08.2007
Записей в блоге: 1
Цитата:
Сообщение от S.Kuskov Посмотреть сообщение

Отсюда вопрос. Какой смысл вручную создавать такой абсурдный с точки зрения приложения индекс (уникальность RecId - это всё же забота ядра и БД).
Первое, что не стоит забывать так это то, что ядро автоматически в любой select добавляет поле RecId, соотвествено такой индекс как написал Андре будет покрывающим (covering index)(в случае выбора только полей индекса без RecId), но стиль программирования в AX не тот, чтобы задумываться об использовании покрывающих индексов (как правило фетчится весь курсор), поэтому ради этого не стали бы создавать данный индекс.

Второе - в AX директива index в запросе не игнорируется и записи сортируются в порядке полей индекса.

Цитата:
Сообщение от S.Kuskov Посмотреть сообщение
И ещё возник такой вопрос. Если уникальность RecId контролируется составным индексом, где помимо RecId присутствуют ещё и другие поля, то уникальность отдельно самого поля RecId, вообще говоря, уже не обеспечивается. Не является ли это потенциальным источником ошибок?
В AX 3.0 маловероятно, поскольку RecId должен быть уникален в разрезе всей компании, а не только таблицы, а вот в DAX 4.0 и старше проблема уже представляется более серьезно

P.S. Насколько мне известно термин "overindexing" означает "перегруженность" таблицы индексами
__________________
Sergey Nefedov

Последний раз редактировалось SRF; 30.07.2009 в 21:22.
Старый 30.07.2009, 21:33   #16  
S.Kuskov is offline
S.Kuskov
Участник
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
 
3,438 / 1775 (66) ++++++++
Регистрация: 28.04.2007
Адрес: Калуга
Цитата:
Сообщение от ZVV Посмотреть сообщение
не путаете, в Аот - не сохраняет, тем не менее где-то запоминает...
Ну раз автоматическое обновление индекса не затрагивает AOT, то тогда ещё раз хочу повторить свой вопрос:

Откуда на SYS слое в AOT уникальне индексы, в составе которых есть поле RecId?
Старый 30.07.2009, 22:01   #17  
lev is offline
lev
Ищущий знания...
Аватар для lev
Oracle
MCBMSS
Axapta Retail User
 
1,723 / 491 (20) +++++++
Регистрация: 18.01.2005
Адрес: Москва
Цитата:
Сообщение от SRF Посмотреть сообщение
В AX 3.0 маловероятно, поскольку RecId должен быть уникален в разрезе всей компании, а не только таблицы
это настраивается, можно сделать и в разрезе таблицы уникальность, но я редко такое встречал, как правило все довольствуются уникальностью в разрезе компании
__________________
"Страх перед возможностью ошибки не должен отвращать нас от поисков истины." (с)
С Уважением,
Елизаров Артем

Последний раз редактировалось mazzy; 05.11.2013 в 15:33.
Старый 30.07.2009, 22:11   #18  
ZVV is offline
ZVV
MCITP
MCP
Oracle
MCBMSS
 
1,006 / 246 (11) ++++++
Регистрация: 13.02.2004
Адрес: Минск
->
Цитата:
Сообщение от lev Посмотреть сообщение
Цитата:
Сообщение от SRF Посмотреть сообщение
В AX 3.0 маловероятно, поскольку RecId должен быть уникален в разрезе всей компании, а не только таблицы
это настраивается, можно сделать и в разрезе таблицы уникальность, но я редко такое встречал, как правило все довольствуются уникальностью в разрезе компании
Редко такое встречали говорите... ))))
Было бы интересно взглянуть хоть на одного...

Включение потабличного RecID в 3-ке
__________________
Zhirenkov Vitaly

Последний раз редактировалось ZVV; 30.07.2009 в 23:13.
Старый 30.07.2009, 23:50   #19  
fed is offline
fed
Moderator
Аватар для fed
Ex AND Project
Соотечественники
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
Лучший по профессии AXAWARD 2013
Лучший по профессии 2011
Лучший по профессии 2009
 
2,907 / 5717 (196) ++++++++++
Регистрация: 13.03.2002
Адрес: Hüfingen,DE
Цитата:
Сообщение от ZVV Посмотреть сообщение
petr, fed -- теперь я понял о чём вы, это всё понятно и верно, но непонятно какое отношение к исходному вопросу?
Топикстартер спрашивает - зачем создавать индексы с фиктивной уникальностью, добавляя поле recid, если в соответствии с информацией из сообщения Проблема с индексами
система сама добавляет поле recId в первый попавшийся индекс и делает его уникальным ?

Отвечаем: Я тут долго рассуждал что уникальность индекса хороша не только потому что она позволяет избежать дубликатов, но и потому что она упрощает обновление индекса и таблицы. Встроенный механизм добавляет поле recId во первых к первому попавшемуся индексу, во вторых только к одному индексу. Для повышения производительности полезно добавлять уникальное поле во все индексы с малой селективностью, а не только в первый попавшийся.

Ну и гипотеза насчет coverage index тоже весьма правдоподобна.
Таким образом - ручное добавление recId в конец некоторых индексов вызвано не необходимостью отслеживания уникальности, а возможностью повысить производительность работы сервера БД с данным индексом.
За это сообщение автора поблагодарили: mazzy (2), ZVV (2), S.Kuskov (1).
Старый 30.07.2009, 23:52   #20  
fed is offline
fed
Moderator
Аватар для fed
Ex AND Project
Соотечественники
Лучший по профессии 2017
Лучший по профессии 2015
Лучший по профессии 2014
Лучший по профессии AXAWARD 2013
Лучший по профессии 2011
Лучший по профессии 2009
 
2,907 / 5717 (196) ++++++++++
Регистрация: 13.03.2002
Адрес: Hüfingen,DE
Цитата:
Сообщение от Андре Посмотреть сообщение
Насколько я помню, Oracle в таких случаях предлагает использовать bitmap-индексы (индексы на основе битовых карт - не уверен в переводе), которые по своей сути не являются деревьями и решают обозначенную тобой проблему.

Правда для того, чтобы Аксапта создавала такие индексы ее придется слегка допилить.
Ну bitmap индексы хороши в тех случаях когда у тебя совсем мало возможных значений у индексного поля - в пределах 10-20. А вот в ситуации когда у тебя в таблице миллион записей и тысяча возможных значений - bitmap слишком тяжел, а обычный b-tree индекс не уникальный слишком тормозит.
Теги
index, indexunique, recid, индекс

 

Похожие темы
Тема Автор Раздел Ответов Посл. сообщение
axperf: Create RecID index on tables with Created/Modified DateTime fields Blog bot DAX Blogs 0 20.06.2009 10:05
Главная книга / Запросы / Аудит (TransactionLog) Зачем и кому он нужен? ta_and DAX: Функционал 18 24.09.2008 10:14
RecId и уникальный индекс York DAX: Программирование 4 25.08.2008 10:47
зачем нужен WebTarget? yooshi DAX: Программирование 0 11.11.2005 14:22
Зачем таблице нужен релэйшн на саму себя? Artild DAX: Программирование 2 21.07.2003 11:52

Ваши права в разделе
Вы не можете создавать новые темы
Вы не можете отвечать в темах
Вы не можете прикреплять вложения
Вы не можете редактировать свои сообщения

BB коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.
Быстрый переход

Рейтинг@Mail.ru
Часовой пояс GMT +3, время: 20:46.