SQLite3:C ++でNULL文字を含むBLOBを挿入する
質問
カスタムデザインのプラグインを使用するC ++ APIの開発に取り組んでいます APIと特定のSQLを使用して異なるデータベースエンジンとインターフェイスする 構文。
現在、BLOBを挿入する方法を探していますが、 NULL
は
C / C ++の終了文字、構築時にBLOBが切り捨てられる
INSERT INTO クエリ文字列。これまでのところ、私は協力してきました
//...
char* sql;
void* blob;
int len;
//...
blob = some_blob_already_in_memory;
len = length_of_blob_already_known;
sql = sqlite3_malloc(2*len+1);
sql = sqlite3_mprintf("INSERT INTO table VALUES (%Q)", (char*)blob);
//...
SQLite3インタラクティブコンソールでできることがあれば、適切にエスケープされた NULL
文字を使用してクエリ文字列を構築できるはずです。たぶん、SQLite SQL構文でもサポートされている標準SQLでこれを行う方法はありますか?
確かに誰かが前に同じ状況に直面したに違いありません。私はグーグルで調べていくつかの答えを見つけましたが、他のプログラミング言語(Python)でした。
ご意見をお寄せいただきありがとうございます。
解決
準備済みステートメントでこの関数を使用します。
int sqlite3_bind_blob(sqlite3_stmt*, int, const void*, int n, void(*)(void*));
C / C ++では、文字列のNULLを処理する標準的な方法は、文字列の先頭と長さを格納するか、文字列の先頭と文字列の末尾へのポインタを格納することです。
他のヒント
ご意見をお寄せいただきありがとうございます。今回は、ここに記載されている指示を参考にして、どのように問題を解決したかを報告しています。これが将来他の人の助けになることを願っています。
最初の3つのポスターで示唆されているように、私は準備されたステートメントを使用しました—さらに、列のデータ型の取得にも興味があり、単純な sqlite3_get_table()
ではできません。
次の定数文字列の形式でSQLステートメントを準備した後:
INSERT INTO table VALUES(?,?,?,?);
対応する値のバインディングのままです。これは、列と同数の sqlite3_bind_blob()
呼び出しを発行することにより行われます。 (他の" simple"データ型については sqlite3_bind_text()
を使用しました。これは、作業中のAPIがintegers / doubles / etcを文字列に変換できるためです)。だから:
void* blobvalue[4];
int blobsize[4];
char *tail, *sql="INSERT INTO table VALUES(?,?,?,?)";
sqlite3_stmt *stmt=0;
sqlite3 *db;
/* ... */
db=sqlite3_open("sqlite.db");
sqlite3_prepare_v2(db,
sql, strlen(sql)+1,
&stmt, &tail);
for(int i=0; i<4; i++)
sqlite3_ bind_ blob(stmt,
i+1, blobvalue[i], blobsize[i],
SQLITE_TRANSIENT);
if(sqlite3_step(stmt)!=SQLITE_DONE)
printf("Error message: %s\n", sqlite3_errmsg(db));
sqlite3_finalize(stmt);
sqlite3_close(db);
また、一部の関数( sqlite3_open_v2()
、 sqlite3_prepare_v2()
)は、後のSQLiteバージョン(3.5.x以降と思われます)に表示されます。
ステートメント sqlite_prepare_v2()
をプリコンパイルし、 sqlite3_bind_blob()
を使用してblobをバインドします。バインドするステートメントは INSERT INTO table VALUES(?)であることに注意してください。