Статьи Королевства Дельфи


Моделирование данных - часть 3


Возможно, эта таблица подойдет для записи всех операций с материалами, но, прежде всего пользователям потребуется отчет об остатках материалов по каждому из имеющихся состояний (в пути, разгружено, оприходовано и пр.) По этой таблице этот отчет строить неудобно: на Inter-base для этого придется написать хранимую процедуру, в которой нужно будет объединить результаты двух запросов, в SQL Server, Oracle, DB2 можно сформулировать всего один запрос для вычисления этих цифр: два запроса объединить конструкцией UNION, а затем с помощью select from select или чего-либо подобного задать окончательные агрегатные вычисления. Этот прием, конечно, сработает, но уже на сотне тысяч записей производительность начнет заметно падать. Вообще, сложные запросы - явный признак неудачной модели данных. В данном случае, нашу таблицу нужно перепроектировать. Каждую операцию перемещения будем кодировать не одной, а двумя записями в таблице: NO - номер операции LN_NO - номер позиции в операции DATE - дата TIME - время MATERIAL - идентификатор материала QUANTITY - количество STATE -состояние

Поле LN_NO будет содержать 0 или 1 и будет частью ключа. В записи для исходного состояния количество запишем с отрицательным знаком (это символизирует тот факт, что материал это состояние покинул), в записи для результирующего состояния знак количества будет положительным.

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

№ опер № поз Дата Время Mатериал Кол-во Состояние
2111 1 28.02.2000 12:28 Спички -100 Принят
2111 2 28.02.2000 12:28 Спички 95 Оприходован
2111 3 28.02.2000 12:28 Спички 5 Брак

Такая схема позволит посчитать остатки одним простым запросом: select STATE, SUM(QUANTITY) from operations group by STATE




Начало  Назад  Вперед