簡體   English   中英

C ++從sqlite3回調函數填充向量?

[英]C++ populate vector from sqlite3 callback function?

我有一個sqlite3表“地址”,像這樣:

+----+------+--------+
| ID | name | number |
+----+------+--------+
| 1  | John | 413434 |
+----+------+--------+

我想填充全局矢量,我可以在其他地方使用並將其與其他數據結合在一起。 到目前為止,我有這個:

...
#include <sqlite3.h>

using namespace std;

static int callbackDB(void *NotUsed, int argc, char **argv, char **szColName)
{
    for(int i = 0; i < argc; i++)
        cout << szColName[i] << " = " << argv[i] << endl;

    return 0;
}

int main(int argc, char* argv[]) {
    vector<vector<string> > table;
    for( int i = 0; i < 2; i++ )
        table.push_back(std::vector< std::string >());


    sqlite3 *db;
    char *szErrMsg = 0;

    // open database
    int rc = sqlite3_open("database.db", &db);

    const char *query;
    query = "SELECT * FROM addresses";

    rc = sqlite3_exec(db, query, callbackDB, 0, &szErrMsg);

    return 0;
}

我如何以矢量或其他方式獲得結果,以便能夠更輕松地使用它?

sqlite3_exec的第四個參數可用於將信息傳遞給回調。 在您的情況下,指向table的指針將很有用:

typedef vector<vector<string> > table_type;
static int callbackDB(void *ptr, int argc, char* argv[], char* cols[])
{
    table_type* table = static_cast<table_type*>(ptr);
    vector<string> row;
    for (int i = 0; i < argc; i++)
        row.push_back(argv[i] ? argv[i] : "(NULL)");
    table->push_back(row);
    return 0;
}
...
    rc = sqlite3_exec(db, query, callbackDB, &table, &errmsg);

但是,使用這樣的回調不是很有用,因為您只會得到一堆裸字符串。 您應該直接使用prepare / step / finalize接口,以便可以使用適當的數據類型:

class Address {
public:
    Address(int id, const string& name, const string& number);
    ...
}

    ...
    vector<Address> addresses;
    sqlite3_stmt *stmt;
    rc = sqlite3_prepare_v2(db, "SELECT id, name, number FROM addresses",
                            -1, &stmt, NULL);
    if (rc != SQLITE_OK) {
        cerr << "SELECT failed: " << sqlite3_errmsg(db) << endl;
        return ...; // or throw
    }
    while ((rc = sqlite3_step(stmt)) == SQLITE_ROW) {
        int id = sqlite3_column_int(stmt, 0);
        const char* name = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1));
        const char* number = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 2));
        // let's assume number can be NULL:
        addresses.push_back(Address(id, name, number ? number : ""));
    }
    if (rc != SQLITE_DONE) {
        cerr << "SELECT failed: " << sqlite3_errmsg(db) << endl;
        // if you return/throw here, don't forget the finalize
    }
    sqlite3_finalize(stmt);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM