C語言:SQLITE3的學習


Sqlite基礎學習

一、sqlite的概念

  SQLite是一款輕型數據庫,是遵守ACID的關系型數據庫管理系統,由C語言開發設計。Sqlite的設計目標着眼於嵌入式領域,所以具有占用系統資源低和處理速度快等特點。

  SQLite是一個進程內的庫,實現了自給自足的、無服務器的、零配置的、事務性的 SQL 數據庫引擎。它是一個零配置的數據庫,這意味着與其他數據庫一樣,您不需要在系統中配置。同時sqlite沒有額外依賴並且完全開源,同時其源碼擁有大量注釋,可讀性非常好。

二、Sqlite的用途

Sqlite支持跨平台,操作簡單,能夠使用很多語言直接創建數據庫。如果你需要做一個很小型的應用,或者你想做嵌入式開發,沒有合適的數據庫系統,那么你可以考慮使用SQLite。例如android系統,IOS系統等都采用了SQLite做為數據庫。

三、Sqlite語法簡介

1SQL簡介

  SQL 是用於訪問和處理數據庫的標准的計算機語言。對於sqlite、mysql、sqlserver等數據庫的操作語言都需要遵循SQL的規范,不過不同的數據庫系統可能對SQL規范作了某些編改和擴充,所以不同數據庫系統之間的SQL不能完全相互通用。

  SQL的一些基本操作:

(1)、面向數據庫執行查詢或取出數據

(2)、往數據庫中插入新的記錄

(3)、更新數據庫中的數據

(4)、從數據庫刪除記錄

(5)、建新數據庫

(6)、在數據庫中創建新表

  其相對應的操作語法大致如下:(以下只是列舉一些語法,並不做說明)

(1)、(SELECT 列名稱 FROM 表名稱),(SELECT DISTINCT 列名稱 FROM 表 名稱),(SELECT 列名稱 FROM 表名稱 WHERE 列 運算符 值),

(SELECT 列名稱1 列名稱2 FROM 表名稱 ORDER BY 列名稱1)等等。

(2)、( INSERT INTO 表名稱 VALUES (值1, 值2,....)),

(INSERT INTO table_name (列1, 列2,...) VALUES (值1, 值2,....))等。

(3)、(UPDATE 表名稱 SET 列名稱 = 新值 WHERE 列名稱 = 某值)等。

(4)、(DELETE FROM 表名稱 WHERE 列名稱 = 值)等。

(5)、(CREATE DATABASE database_name)等。

(6)、CREATE TABLE 表名稱

(

列名稱1 數據類型,

列名稱2 數據類型,

列名稱3 數據類型,

....

)

2Sqlite3常用函數說明

SQLITE_API int sqlite3_open(
  const char *filename,   /* Database filename (UTF-8) */
  sqlite3 **ppDb          /* OUT: SQLite db handle */
);
函數說明:該程序會通過指定的文件名參數打開一個數據庫文件
數據庫的連接返回到*ppDb,函數的返回值代表了操作狀態,例如成功
就返回SQLITE_OK,否則返回錯誤代碼和意外情況下不能分配內存來的得到
sqlite3就返回NULL

SQLITE_API int sqlite3_close(sqlite3*);
函數說明:前面如果用 sqlite3_open 開啟了一個數據庫,結尾時不要忘了用這個函數關閉數據庫
同樣返回值為操作狀態

SQLITE_API int sqlite3_exec(
  sqlite3*,                                  /* An open database */
  const char *sql,                           /* SQL to be evaluated */
  int (*callback)(void*,int,char**,char**),  /* Callback function */
  void *,                                    /* 1st argument to callback */
  char **errmsg                              /* Error msg written here */
);
函數說明:該函數為具體執行SQL語句的函數
參數1:打開的數據庫連接對象
參數2:傳入的SQL語句,以‘/0’結尾
參數3:是回調函數,如果傳入參數不為NULL,則得到一個結果行就會調用該回調函數
參數4:自定義的一個指針,目的是傳入到回調函數參數以供使用。
參數5:錯誤信息,如果語句執行失敗,就可以查閱該指針,這里的參數是輸出特性
    (即主調函數將類型變量的地址傳入,函數分配內存賦值給該變量)
    同時在執行完該函數后又不需要錯誤信息時,為了避免內存泄露,應該調用
    sqlite3_free()來釋放這塊內存
返回值:操作狀態

SQLITE_API int sqlite3_get_table(
  sqlite3 *db,          /* An open database */
  const char *zSql,     /* SQL to be evaluated */
  char ***pazResult,    /* Results of the query */
  int *pnRow,           /* Number of result rows written here */
  int *pnColumn,        /* Number of result columns written here */
  char **pzErrmsg       /* Error msg written here */
);
函數說明:與sqlite3_exec功能相同,只是不使用回調函數而是直接一張表的內存和行與列
參數1:打開的數據庫連接對象
參數2:該參數為輸出特性,目的是函數內部返回一張表給主調函數使用,最終使用完需要
    釋放是,不能調用 sqlite3_free() 而是要調用 sqlite3_free_table()來做釋放
參數3:該參數為輸出特性,修改pnRow的值為表的行數
參數4:該參數為輸出特性,修改pnColumn的值為表的列數
參數5:錯誤信息,如果語句執行失敗,就可以查閱該指針,這里的參數是輸出特性
    同時在執行完該函數后又不需要錯誤信息時,為了避免內存泄露,應該調用
    sqlite3_free()來釋放這塊內存
返回值:操作狀態

這些是比較常用的函數,至於更多的函數則不在多舉例。

四、sqlite3使用例子

    1、操作數據庫的一個簡單例子(代碼參考自別人)

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<sqlite3.h>
static int loadMyInfo(void* para, int column, char** columnValue,char** columnName)
{
    int i = 0;
    for (i = 0; i < column; i++)
    {
        printf("field name:%s    ------>        field values:%s\n", columnName[i],columnValue[i]);
    }
    printf("------------------------------------------------------\n");
    return 0;
}
int main(void)
{
    sqlite3 *db = NULL;
    int result;
    char *errMsg = NULL;
    //打開數據庫
    //傳如sqlite3*類型變量的地址
    result = sqlite3_open("/home/sns/workspace/database.db", &db);
    if (result != SQLITE_OK)
    {
        printf("database open fail!\n");
        return -1;
    }
    //TODO    數據庫操作代碼
    //sqlite的操作語句不區分大小寫
    //創建一個數據表,表名為MyTabale1,分兩個字段:ID和name。
    //其中ID是一個自動增加的整型,之后insert可以不去指定這個字段,它會自己從0開始增加
    //name為一個含 32 個字符的可變長度 Unicode 字符數據.
    result =sqlite3_exec(db,
                    "create table MyTable1(ID Integer primary key autoincrement,name nvarchar(32))",
                    NULL, NULL, &errMsg);    //(字段名 字段類型 SQL約束)
    if (result != SQLITE_OK)
    {
        printf("create a table fail!,fail code:%d,fail reason:%s\n", result,
                errMsg);
    }
    if (errMsg != NULL)
    {
        sqlite3_free(errMsg);
        errMsg = NULL;
    }
    //往表中插入三條記錄
    result = sqlite3_exec(db, "insert into MyTable1(name) values('zoulu')",NULL, NULL, &errMsg);
    if (result != SQLITE_OK)
    {
        printf("insert a record fail!,fail code:%d,fail reason:%s\n", result,
                errMsg);
    }
    if (errMsg != NULL)
    {
        sqlite3_free(errMsg);
        errMsg = NULL;
    }
    result = sqlite3_exec(db, "insert into MyTable1(name) values('qidanche')",NULL, NULL, &errMsg);
    if (result != SQLITE_OK)
    {
        printf("create a record fail!,fail code:%d,fail reason:%s\n", result,
                errMsg);
    }
    if (errMsg != NULL)
    {
        sqlite3_free(errMsg);
        errMsg = NULL;
    }
    result = sqlite3_exec(db, "insert into MyTable1(name) values('zuofeiji')",
            NULL, NULL, &errMsg);
    if (result != SQLITE_OK)
    {
        printf("create a record fail!,fail code:%d,fail reason:%s\n", result,
                errMsg);
    }
    if (errMsg != NULL)
    {
        sqlite3_free(errMsg);
        errMsg = NULL;
    }
//    查詢數據庫
    result = sqlite3_exec(db, "select * from MyTable1", loadMyInfo, NULL,&errMsg);
    if (errMsg != NULL)
    {
        sqlite3_free(errMsg);
        errMsg = NULL;
    }

    //不使用回調函數查詢數據庫
    char **dbResult = NULL;
    int nRow, nColumn;
    int index;
    int i, j;
    result = sqlite3_get_table(db, "select * from MyTable1", &dbResult, &nRow,&nColumn, &errMsg);
    if (result == SQLITE_OK)
    {
        index = nColumn;
        printf("find %d record\n", nRow);

        for (i = 0; i < nRow; i++)
        {
            for (j = 0; j < nColumn; j++)
            {
                printf("field name:%s    ------>        field values:%s\n", dbResult[j],
                        dbResult[index]);
                index++;
            }
            printf(
                    "----------------------------------------------------------\n");
        }
    }

    sqlite3_free_table(dbResult);
    //關閉數據庫
    sqlite3_close(db);
    return EXIT_SUCCESS;
}
code1

     2、存取和讀出二進制數據

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<sqlite3.h>
//sqlite 存取和讀出二進制數據,需要使用sqlite3的sqlite3_stmt
int main(void)
{
    sqlite3 *db1 = NULL;
    char *errMsg=NULL;//保存錯誤信息
    int result = 0;
    result = sqlite3_open("/home/sns/workspace/binarydatabase.db",&db1);
    if(result!=SQLITE_OK)
    {
        printf("database open fail!\n");
        return -1;
    }
    //數據庫操作 :
    result = sqlite3_exec(db1,"create table BinTable2(ID integer,content blob)",NULL,NULL,&errMsg);
    if(result != SQLITE_OK)
    {
        printf("create a table fail!,fail code:%d fail reason:%s",result,errMsg);
        return -1;
    }
    //寫入二進制內容
    sqlite3_stmt *stat;
    void *pdata="hjktgagagf";
    result = sqlite3_prepare( db1, "insert into BinTable2( ID, content) values( 10, ? )", -1, &stat, 0 );
    if(result == SQLITE_OK && stat!=NULL)
    {
        sqlite3_bind_blob(stat,1,pdata,sizeof(pdata),NULL);
        printf("pdata length:%ld\n",sizeof(pdata));
        result= sqlite3_step(stat);
        if(result!=SQLITE_OK)
        {
            printf("write fail!\n");
        }
    }
    if(stat)
    {
        sqlite3_finalize(stat);
    }
    //讀出數據庫記錄
    sqlite3_stmt *stat1=NULL;
    result = sqlite3_prepare( db1, "select * from BinTable2", -1, &stat1, 0 );
    if(result==SQLITE_OK)
    {
            result = sqlite3_step(stat1);
            printf("result:    %d\n",result);
            if(result==SQLITE_ROW)
            {
                int id = sqlite3_column_int(stat1,0);
                const void * content = sqlite3_column_blob(stat1,1);
                int len = sqlite3_column_bytes(stat1,1);
                printf("\nid = %d,sizeof(content) = %d !\n",id,len);
            }
    }
    if(stat1)
    {
        sqlite3_finalize(stat1);
    }
    //關閉數據庫
    sqlite3_close(db1);
    return EXIT_SUCCESS;
}
code2

 五:擴展說明

  關於sqlite3的C語言使用可以更多的關注該作者:https://home.cnblogs.com/u/elect-fans/

  本文第四項的操作二進制代碼的說明請參考

    基於SQLITE數據庫的C語言編程


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM