- Знакомство с принципами работы с базой данных в MQL5
- Основы SQL
- Структура (схема) таблиц: типы данных и ограничения
- Интеграция ООП (MQL5) и SQL: концепция ORM
- Создание, открытие и закрытие базы данных
- Выполнение запросов без привязки к данным MQL5
- Проверка существования таблицы в базе данных
- Подготовка запросов с привязкой: DatabasePrepare
- Удаление и сброс подготовленных запросов
- Привязка данных к параметрам запроса:DatabaseBind/Array
- Выполнение подготовленных запросов: DatabaseRead/Bind
- Раздельное чтение полей: DatabaseColumn-функции
- Примеры CRUD-операций в SQLite через объекты ORM
- Транзакции
- Импорт и экспорт таблицы базы данных
- Печать таблиц и SQL-запросов в журнал
- Пример поиска торговой стратегии средствами SQLite
Привязка данных к параметрам запроса:DatabaseBind/Array
После того как SQL-запрос был откомпилирован функцией DatabasePrepare, можно использовать полученный дескриптор запроса для привязки данных к параметрам запроса, для чего предназначены функции DatabaseBind и DatabaseBindArray. Обе функции можно вызывать не только сразу после создания запроса в DatabasePrepare, но и после сброса запроса в начальное состояние с помощью DatabaseReset (если запрос выполняется много раз в цикле).
Этап привязки данных требуется не всегда, поскольку подготовленные запросы могут и не иметь параметров. Как правило, такая ситуация возникает, когда запрос возвращает данные из SQL в MQL5, в связи с чем требуется дескриптор запроса: о том, как читать результаты запросов по их дескриптору, рассказано в разделах о функциях DatabaseRead/DatabaseReadBind и DatabaseColumn-функциях.
bool DatabaseBind(int request, int index, T value)
Функция DatabaseBind устанавливает для запроса с дескриптором request значение параметра с индексом index. По умолчанию нумерация начинается с 0, если параметры в запросе помечены подстановочными символами '?' (без номера). Однако, параметры могут обозначаться в строке запроса и с номером (?1, '?5', ?21): в таком случае фактические индексы, которые следует передавать в функцию, должны быть на 1 меньше, чем соответствующий номер в строке. Дело в том, что в строке запроса нумерация ведется с 1.
Например, для следующего запроса требуется задать один параметр (индекс 0):
int r = DatabasePrepare(db, "SELECT * FROM table WHERE id=?");
|
Если бы в строке запроса использовалась подстановка "... id=?10", потребовалось бы вызвать DatabaseBind с индексом 9.
Значение value в прототипе DatabaseBind может быть любого простого типа или строкой. Если параметру требуется сопоставить данные составного типа (структуры) или произвольные двоичные данные, которые можно представить в виде массива байтов, используйте функцию DatabaseBindArray.
Функция возвращает true в случае успеха, а иначе — false.
bool DatabaseBindArray(int request, int index, T &array[])
Функция DatabaseBindArray устанавливает для запроса с дескриптором request значение параметра с индексом index как массив простого типа или простых структур (включая строки). Эта функция позволяет записывать в базу данных BLOB и NULL (отсутствие значения, которое считается в SQL самостоятельным типом и не равно 0).
Вернемся к классу DBQuery в файле DBSQLite.mqh и поддержим в нем привязку данных.
class DBQuery
|
BLOB подойдет для переноса в базу любого файла в неизменном виде, например, если предварительно прочитать его в байтовый массив с помощью функции FileLoad.
Необходимость явной привязки значения NULL не так очевидна. Дело в том, что при вставке новых записей в базу вызывающая программа обычно передает только известные ей поля, а все недостающие (если они не помечены ограничением NOT NULL или не имеют иного значения DEFAULT в описании таблицы), "движок" автоматически оставит равными NULL. Однако при использовании подхода ORM бывает удобно записать в базу объект целиком, включая и поле с уникальным первичным ключом (PRIMARY KEY). В новом объекте этого идентификатора еще нет, так как его проставляет сама база при первой записи объекта, поэтому важно привязать это поле в новом объекте к значению NULL.