Запись и чтение данных в SQLite3 на с++

202
14 августа 2017, 10:59

Добрый день! Как правильно записать данные в sqlite, и соответственно считать их на с++? Данные представляют собой несколько переменных разных типов, числа, символы, всего 10 элементов. Запись производится каждые 10 секунд, примерно по 40 строк (отсюда возникает еще один вопрос, как оптимальнее загружать данные).

На хабре нашел интересную статью, где автор подробно объясняет об особенностях sqlite. Там же, он прилагает код работы с этой бд:`

#include <stdio.h>
#include "sqlite3.h"
const char* SQL = "CREATE TABLE IF NOT EXISTS foo(a,b,c); INSERT INTO FOO 
VALUES(1,2,3); INSERT INTO FOO SELECT * FROM FOO;";
int main(int argc, char **argv){
sqlite3 *db = 0; // хэндл объекта соединение к БД
char *err = 0;
// открываем соединение
if( sqlite3_open("my_cosy_database.dblite", &db) )
fprintf(stderr, "Ошибка открытия/создания БД: %s\n", sqlite3_errmsg(db));
// выполняем SQL
else if (sqlite3_exec(db, SQL, 0, 0, &err))
{
fprintf(stderr, "Ошибка SQL: %sn", err);
sqlite3_free(err);
}
// закрываем соединение
sqlite3_close(db);
return 0;
}`

Код работает, БД создается, все отлично. Вопрос в том, как мне формировать sql запрос автоматически, т.е. получается, что char* SQL является константным значением, и например если я захочу добавить к запросу SQL переменную, которая будет постоянно обновляться, то будет возникать соответствующая ошибка, пример:

char* for_ins= "foooo"; char* SQL_check = "CREATE TABLE IF NOT EXISTS foo(a,b,c); INSERT INTO foo" + for_ins; ошибка:

char *foo_ins выражение должно относиться к целочисленному типу или типу перечисления без области видимости

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

Answer 1

Ошибка в коде.

char* for_ins= "foooo"; char* SQL_check = "CREATE TABLE IF NOT EXISTS foo(a,b,c); INSERT INTO foo" + for_ins;

Стандартный компилятор MS VS 2013 в данном случае выдаёт ошибку:

Error   1   error C2110: '+' : cannot add two pointers

Что собственно логично.

Если нет ограничений на использование библиотеки std, рекомендую для данных целей воспользоваться std:string и std::string::c_str() для получения const char*:

 std::string for_ins = "foooo";
 std::string SQL_check = "CREATE TABLE IF NOT EXISTS foo(a,b,c); INSERT INTO foo" + for_ins;
 puts(SQL_check.c_str());

Пример использования SQLite

bool foo(const string &date, const string &product_id, const string &material_id, const string &order_id){
    string statistic_query = string("INSERT INTO MY_TABLE(date, ProductId, MaterialId, orderId)") +
    "VALUES (\"" + date + "\", \"" + product_id + "\", \"" + material_id + "\", \"" + order_id + "\");";
    request_status = sqlite3_exec(statistic_db, statistic_query.c_str(), Callback, 0, &m_error_mesage);
    if (request_status != SQLITE_OK) 
    {
        //Something went wrong
        return false;
    }
}

Оптимальность

Оптимальность - понятие относительное. Если считаешь, что приложение будет работать штатно (не будет скачков напряжения и перезагрузок, никто не будет убивать процесс), то я бы формировал временные очереди на 40 сообщений, используя BEGIN TRANSACTION и потом бы уже пачку коммитил. Пример из обучающего урока (SQLite transaction tutorial):

BEGIN TRANSACTION;
INSERT INTO account_changes(account_no,flag,amount,changed_at) values(100,'-',1000,datetime('now'));
INSERT INTO account_changes(account_no,flag,amount,changed_at) values(200,'+',1000,datetime('now'));
COMMIT;
READ ALSO
Объединение нескольких send&#39;ов в один recv

Объединение нескольких send'ов в один recv

Может ли случиться так, что все данные, посланные несколькими операциями send(), на хосте назначения будут считаны всего одним вызовом recv()?

215
Клик по элементу и вне области элемента

Клик по элементу и вне области элемента

Здравствуйте! Вот мой Jquery:

339
Некорректно работает :nth-child

Некорректно работает :nth-child

Сайт написан на OpenCart версии 2x

228
Нужна помощь в написании простого теста для spring-boot

Нужна помощь в написании простого теста для spring-boot

Есть простой репозиторий и сервис на spring-boot надо написать на него тестПомогите пожалуйста

337