Книга: Мир InterBase. Архитектура, администрирование и разработка приложений баз данных в InterBase/FireBird/Yaffil
"Низкоуровневая" работа с внутренним буфером TpFIBDataSet
"Низкоуровневая" работа с внутренним буфером TpFIBDataSet
TpFIBDataSet включает несколько специальных методов для работы с внутренним буфером, в котором хранятся записи. В общем-то, данные методы превращают TpFIBDataSet в аналог TClientDataSet, ориентированный на InterBase. Наиболее интересным примером использования данных методов будет, пожалуй, построение диалога выбора, состоящего из двух списков (рис. 2.75).
Рис 2.75. Использование локального кеша TpFIBDataSet для организации двойного списка выбора
В данном примере мы будем использовать базу данных EMPLOYEE.GDB, входящую в стандартную поставку InterBase и FIBPlus. Покажем запросы для SourceDS:
SelectSQL:
SELECT
CUS.CUST_NO,
CUS.CUSTOMER
FROM
CUSTOMER CUS
ORDER BY CUS.CUSTOMER
UpdateSQL:
UPDATE CUSTOMER SET
CUSTOMER = ?CUSTOMER
WHERE
CUST_NO = ?OLD_CUST_NO
InsertSQL:
INSERT INTO CUSTOMER(
CUST_NO,
CUSTOMER
VALUES(
?CUST_NO,
?CUSTOMER
DeleteSQL:
DELETE FROM CUSTOMER
WHERE
CUST_NO = ?OLD_CUST_NO
RefreshSQL:
SELECT
CUS.CUST_NO,
CUS.CUSTOMER
FROM
CUSTOMER CUS
WHERE
CUS.CUST_NO = ?OLD_CUST_NO
Те же самые запросы мы будем использовать в TargetDS, поскольку оба компонента должны обладать совместимой структурой полей. Откроем оба запроса сразу после создания формы:
procedure TDualListForm.FormCreate(Sender: TObject);
begin
SourceDS.Open;
TargetDS.CacheOpen;
end;
Если мы не указываем в коде явного открытия базы данных, то это означает, что свойство Connected > компонета TpFlBDatabase было задано в True в design-time.
Обратите внимание на то, что TargetDS мы активируем при помощи специального метода CacheOpen. Этот метод не выполняет запрос из SelectSQL, а только подготавливает внутренний буфер компонента в зависимости от запроса в SelectSQL. Очевидно, что после запуска приложения мы увидим записи в левом списке и пустую таблицу в правом. Теперь мы можем написать процедуру, которая позволит переносить записи из одного списка в другой:
procedure TDualListForm.MoveRec(Select: Boolean);
begin
if Select then begin
if (SourceDS.Active) and (not SourceDS.IsEmpty) then begin
TargetDS.CacheRefreshByArrMap(SourceDS, frklnsert,
['CUST_NO'], ['CUST_NO']);
SourceDS.CacheDelete;
end;
end
else begin
if (TargetDS.Active) and (not TargetDS.IsEmpty) then begin
SourceDS.CacheRefresh(TargetDS, frklnsert, nil);
TargetDS.CacheDelete;
end;
end;
end;
Если параметр Select равен True, то мы будем переносить текущую запись из левого списка в правый, т. е. из SourceDS в TargetDS. Рассмотрим подробнее метод CacheRefreshByArrMap.
procedure CacheRefreshByArrMap(FromDataSet: TDataSet; Kind:
TCachRefreshKind; const SourceFields, DestFields: array of
String);
Метод позволяет вставлять или модифицировать текущую запись в локальный буфер компонента, т. е. без выполнения соответствующих модифицирующих запросов. Параметр FromDataSet указывает, из какого TpFIBDataSet мы хотим получить запись. Параметр Kind может принимать два значения: frkEdit или frklnsert. Frklnsert указывает, что мы хотим вставить новую запись, a frkEdit - что мы хотим изменить существующую. Параметр SourceFields описывает список полей из компонента источника, а список DestFields - список полей в TpFIBDataSet-приемнике. Формально названия полей в списках могут не совпадать, но необходимо, чтобы совпадали типы данных, иначе обмен данными будет невозможен. В нашем примере, как вы можете видеть, мы вставляем в TargetDS текущую запись из SourceDS. Данный метод использован здесь только для демонстрации, поскольку мы вполне могли бы обойтись методом CacheRefresh, который копирует соответствующие поля автоматически. После вставки записи необходимо удалить ее из компонента источника. Это делается при помощи метода CacheDelete, который также не выполняет соответствующий запрос (DeleteSQL), а удаляет запись только из локального буфера в памяти. Теперь, когда мы знаем, что делают процедуры CacheRefreshByArrMap, CacheRefresh и CacheDelete, код процедуры достаточно очевиден: мы копируем запись из компонента-источника в компонент-приемник и удаляем ее из компонента-источника.
То же самое можно сделать в цикле, если мы хотим перенести все записи сразу:
procedure TDualListForm.MoveAll(Select: Boolean);
var TmpDataSet: TpFIBDataSet;
begin
if Select then TmpDataSet := SourceDS else
TmpDataSet := TargetDS;
with TmpDataSet do begin
try
DisableControls;
First;
while not Eof do MoveRec(Select);
finally
EnableControls;
end;
end;
end;
Остается написать обработчики события OnClick для кнопок:
procedure TDualListForm.ButtonlClick(Sender: TObject);
begin
MoveRec(True); // SourceDS -> TargetDS
end;
procedure TDualListForm.Button2Click(Sender: TObject);
begin
MoveRec(False); // TargetDS -> SourceDS
end;
procedure TDualListForm.Button3Click(Sender: TObnect);
begin
MoveAll(True), // SourceDS -> TargetDS
end;
procedure TDualListForm. Button4Click (Sender : TObject) ;
begin
MoveAll(False); // TargetDS -> SourceDS
end;
Мы можем запустить наше приложение (рис 2.76)
Если мы будем нажимать на кнопку Button 1, то записи будут переноситься из левого списка в правый (рис. 2 77).
Все операции осуществляются только с данными внутри локальных буферов, не затражвают сервер и реальные данные в базе Наряду с описанными выше методами вы также можете использовать.
OpenAsCIone - открыть DataSet и скопировать данные из другого DataSet
CacheAppend - добавить запись в конец локального буфера.
SwapRecords - обменять записи в локальном буфере.
CacheEdit - задать значения полей у записи в локальном буфере.
Cachelnsert - вставить запись в локальный буфер
CacheModify - общий метод для вставки и изменения записи в локальным буфере
LoadFromFile - заполнить локальный буфер записями из файла.
LoadFromStream - заполнить локальный буфер записями из потока.
SaveToFile - сохранить локальный буфер в файл.
SaveToStream - сохранить локальный буфер в потоке
Функции работы с локальным буфером предоставляют разработчику чрезвычайно гибкое средство манипуляции данными в клиентских приложениях, позволяя улучшать наглядность пользовательского интерфейса без выполнения дополнительных запросов к базе данных
Рис 2.76. Внешний вид запущенного приложения
Рис 2.77. Внешний вид приложения при выборе пользователем трех записей
- Обработка потери подключения к базе данных
- Эмуляция Boolean-полей
- Поддержка array-полей. Пример использования TpFIBUpdateObject и TDataSetContainer
- Работа с BLOB-полями
- Локальная сортировка и локальная фильтрация
- Обработка событий InterBase при помощи FIBPIus
- "Низкоуровневая" работа с внутренним буфером TpFIBDataSet
- Практическая работа 53. Запуск Access. Работа с объектами базы данных
- Восстановление "безнадежных" баз данных. InterBase Surgeon
- Основные "рычаги" управления производительностью
- Лекция 15. Работа с базами данных
- Работа с ресурсами локальной сети
- Эффективная работа с временными файлами сортировки
- Ускоренная работа с индексами
- HR-брендинг: Работа с поколением Y, новые инструменты для коммуникации, развитие корпоративной культуры и еще 9 эффектив...
- Безопасная работа с внешними таблицами
- Работа со строками
- 9.2. Работа прокси-сервера
- 3. Заработок для фотографов: заработать на фото – сайты фотобанков