我有下面的代碼可以在Sqlite數據庫中插入數據,但它太慢了。 Sqlite FAQ說它一次可以支持50K的插入。我附上了以下代碼。Sqlite C++插入很慢
SqliteBuffer.h
#ifndef SQLITE_BUFFER_H
#define SQLITE_BUFFER_H
#include "sqlite3.h"
#include <iostream>
class SqliteBuffer
{
std::string db_name_;
sqlite3 *db_;
sqlite3_stmt *insert_stmt_;
bool has_transaction_begun;
public:
SqliteBuffer(std::string db_name);
~SqliteBuffer();
int CreateTable();
void SaveMessage(std::string msg);
void BeginTransaction();
void EndTransaction();
};
#endif
SqliteBuffer.cc
#include "SqliteBuffer.h"
int SqliteBuffer::CreateTable()
{
sqlite3_stmt *create = NULL;
if(sqlite3_prepare_v2(db_,"CREATE TABLE mytable (sif INTEGER PRIMARY KEY, log VARCHAR);",-1,&create,NULL)==SQLITE_OK){
sqlite3_step(create);
sqlite3_finalize(create);
}
return 0;
}
SqliteBuffer::SqliteBuffer(std::string db_name)
{
int rc = sqlite3_open_v2(db_name.c_str(), &db_, SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE, NULL);
if(rc!=SQLITE_OK){
sqlite3_close_v2(db_);
}
CreateTable();
rc = sqlite3_prepare_v2(db_, "INSERT INTO mytable(log) VALUES (@LOG)", -1, &insert_stmt_, NULL);
}
void SqliteBuffer::SaveMessage(std::string message)
{
BeginTransaction();
sqlite3_bind_text(insert_stmt_,1,message.c_str(),-1,SQLITE_TRANSIENT);
sqlite3_step(insert_stmt_);
sqlite3_clear_bindings(insert_stmt_);
sqlite3_reset(insert_stmt_);
}
void SqliteBuffer::BeginTransaction()
{
if(has_transaction_begun == false){
has_transaction_begun = true;
sqlite3_exec(db_, "BEGIN TRANSACTION;",NULL,NULL,NULL);
}
}
void SqliteBuffer::EndTransaction()
{
if(has_transaction_begun == true){
has_transaction_begun = false;
sqlite3_exec(db_, "END TRANSACTION;",NULL,NULL,NULL);
}
}
main.cc
#include "SqliteBuffer.h"
int main()
{
SqliteBuffer *sql = new SqliteBuffer("E:\\asdf.db");
for(int i(0); i<2000; i++){
sql->SaveMessage("HELLO WORLD");
}
return 0;
}
我在Visual Studio 10中測試了這些代碼,它們工作正常,但插入非常慢。我在這裏錯過了什麼。
由於您從不初始化'has_transaction_begun',因此程序未定義。 – molbdnilo
您*必須*檢查所有'sqlite3_ *'函數的返回值。由於molbdnilo顯示錯誤,最後一個'sqlite3_exec'將失敗(因爲沒有活動事務)。 –
是的,我將檢查完整代碼中的錯誤。當我製作原型時,除非速度非常慢,否則此工作正常。 – Pant