Форум: "Базы";
Текущий архив: 2002.10.03;
Скачать: [xml.tar.bz2];
ВнизАгрегатные поля Найти похожие ветки
← →
REA (2002-09-11 10:52) [0]Никто не сталкивался с агрегатными полями?
Понадобилось сделать ко всему прочему (см. вопрос о вставке записей в нумерованную таблицу) сделать агрегатные поля. Т.е. сумма предыдущих значений по заданным полям с накоплением: 1,2,3 -> 1,3,6 и т.п. Встроенными средствами BDE это не организовать. Дергать курсор в OnCalc не хочется. Можно использовать client dataset ( в D7 TBDEClientDataset уже отсутствует :( ) установить провайдера и прочую лабуду, но тут опять встает проблема с нумерацией.
← →
Nikolai_S (2002-09-11 11:22) [1]Возможно поможет SQL-запрос. Можно ведь составить сложный SQL-запрос, который будет рассчитывать все, что нужно. Здесь уже зависит от конкретной задачи. Но в этом случае таблица c данными будет не редактируемой. Вот пример такого запроса:
SELECT Field1, Field2, (SELECT Sum(Field2) FROM MyTable WHERE <условие, какие поля суммировать>) FROM MyTable AS MyTable1
← →
REA (2002-09-11 11:29) [2]Запрос пробовал. Поскольку мне нужно на конкретную запись иметь информацию при установке на нее (или лучше по всем записям одновременно) то приходится вешать его на OnScroll. Выполняется долго (порядка 100мс). Вычисляемые агрегатные поля не нужно редактировать. Собственно можно сделать даже и не поля, а одно число для справки - сумма по такому то полю по текущую запись.
← →
Sergey13 (2002-09-11 11:40) [3]-Ну запросы у вас, - сказала база данных.. и повисла 8-)
Что то ты сильно много хочешь, да при этом чтобы все летало. СтОит, ИМХО, подумать - а надо ли все это?
← →
REA (2002-09-11 12:03) [4]Я сейчас пробую сделать вычисляемое поле и делать пересчет в кэш при открытии, вставке, редактировании и удалении, а потом доставать из кэша. Пока проблема только в том, что надо знать число записей и номер текущей в OnCalc, а RecNo вроде для всех поддерживается. Придется наверно в кэше по индексу искать.
А есть ли возможность исполнить SQL запрос на данные, которые уже в памяти ClientDataSet? Я бы тогда его использовал.
← →
Nikolay M. (2002-09-11 13:08) [5]А почему бы не заюзать MemoryTable из RX? Открыл запрос, присвоил некоторой накапливаемой переменной AggFieldValue нулевое значение и побежал по вернувшемуся НД, делая каждый раз Inc (AggFieldValue, Query1.FieldByName ("Field").AsInteger) и заносить это значение в дополнительное поле MemoryTable. Правда, придется мучиться с редактированием записей...
А еще можно повесить на OnAfterOpen создание массива записей, где первичному ключу НД соотвествует это аггрегирующее поле. А в OnCalcFields уже лезть в этот кэш.
← →
REA (2002-09-11 16:58) [6]Первый подход эквивалентен TClientDataSet, но у меня идет активная работа с таблицей и кэшированный апдейт не лучший выход. Сделал с кэшем, хотя тоже не так все просто там.
← →
MsGuns (2002-09-11 18:46) [7]Господи Иисусе, да как же все офигенно сложно !
Может не траву надо пересаживать по перочинный ножик, а просто взять косу ?;)))
По-моему, здесь явно все искусственно усложнено (интуиция)
← →
REA (2002-09-12 10:29) [8]Да хоть бензопилу возьми - агрегатных полей то нету. Мне нужна статистика по каждому элементу за предыдущий интервал причем в динамике - записей там немного. Можно по кнопке суммировать, но юзеров это напрягает.
← →
Sergey13 (2002-09-12 11:39) [9]Ну усли записей не много то см. Nikolay M. © (11.09.02 13:08)
Только вставлять значения можно не запросом а просто пробежаться в цикле и вставлять в 1 поле порядковй номер +1, а во второе нарастающую сумму первого поля. Свяжи RxMemoryData и твой датасет по afterscroll и бегай по нему сколько хочешь. Редактирование и удаление проблем вызвать не должны, с вставкой придется помучаться, но, ИМХО, решаемо.
← →
REA (2002-09-12 11:51) [10]>>Редактирование и удаление проблем вызвать не должны, с вставкой придется помучаться, но, ИМХО, решаемо.
А чем оно лучше чем ClientDataSet? Я принципиально не использую сторонние компоненты даже с исходным кодом - сложно переходить с версии на версию.
Со вставкой намучался уже (см. вопрос про таблицу с автонумерацией записей). SQL запрос ведь на такую таблицу не наслать? Придется писать эквивалентный код руками, а это не проще чем делать кэш и потом все это надо еще обратно в таблицу загнать будет.
← →
MsGuns (2002-09-12 12:48) [11]>REA (12.09.02 10:29)
>Да хоть бензопилу возьми - агрегатных полей то нету. Мне нужна статистика по каждому элементу за предыдущий интервал причем в динамике - записей там немного. Можно по кнопке суммировать, но юзеров это напрягает.
Ну, бензпоилой много не накосишь..8)
Я бы эту проблему решал с помощью доп.таблиц БД "Динамика",
примерно такой структуры
1.Таблица элементов (Master): 1 PRIMARY REY
Код (идентификатор) элемента (Мастер Ключ)
Количество замеров
Суммовые характеристики
Дата+Время последнего замера
2.Таблица замеров (Detail) 2 PRIMARY REYS
Код (идентификатор) элемента (Внешний ключ)
Дата+время замера (Внутр.ключ)
Характеристики замеров
При изменении данных в осн.БД модификации (назовем их замерами)
автоматически (например, по триггеру AfterPost), отражаются сначала в Табл.замеров, а после ее пересчета итоги переносятся в таблицу элементов.
Все это на таблицах до 20000 записей будет работать достаточно быстро.
И главное, удобно получать инфу не только суммовую, но и типа "с нарастающими итогами" за любой промежуток времени.
← →
MsGuns (2002-09-12 12:55) [12]Внимательнее перечитал весь сабж и делаю поправку к своему "рецепту".
Если нет необходимости держать "итоговый" штамм по элементу, то первая таблица, в общем, не нужна. Достаточно только таблицы замеров. Но она д.б. привязана по ключам (индексам) к основной и тогда в любой записи осн.таблицы "лезем" в эту таблицу и SQL-м и определяем сумму ПО ВРЕМЯ = ВРЕМЯ текущей записи осн.БД
Страницы: 1 вся ветка
Форум: "Базы";
Текущий архив: 2002.10.03;
Скачать: [xml.tar.bz2];
Память: 0.48 MB
Время: 0.01 c