数据库
         sun
         solaris  gnu
 1、分类: 大型    中型            小型
          ORACLE   MYSQL/MSSQL   SQLITE  DBII powdb
         关系型数据库        
 2、名词:
         DB        数据库 select update database
         DBMS    数据库管理系统
         MIS     管理信息系统
         OA      办公自动化
 3、嵌入式数据库:
         sqlite3    www.sqlite.org  www.kernal.org
     GNU   
     特点:
           1、开源  C语言开发
           2、代码量少 1万行左右,总大小10M以内
           3、绿色软件无需安装
           4、文件型数据库,可以移动。
           5、数据容量最大 2T   
           
 whereis sqlite3
 sqlite3:
4、sqlite3的安装: LTS long term support 
      1、在线安装 :
                 sudo apt-get install sqlite3 
                 sudo apt-get install libsqlite3-dev
    
         gcc test.c -lsqlite3 -lpthread
         
     2、验证是否安装成功:
         sqlite3 --version
         sqlite3 --help
5、sqlite3的使用:
     0、启动sqlite3 
             sqlite3 xxx.db  
             ===>用sqlite3 来打开一个名称为test.db的本地数据库。
            出现如下提示符:表明数据库管理系统启动。
             sqlite> 
              退出数据库: 
                .q 命令
             
             注意:如果一直出现如下符号:
             ...>   
             则写';'结束。
以下所有命令必须在 sqlite> 后执行。
    创建一个数据库:
         1、touch  xxx.db
         2、sqlite3 xxx.db
    1、系统维护命令:===> .help
         出现所有相关的系统维护命令,都是以 "."开头。
         .database  列出当前库和系统中那个文件在关联
         .tables    列出当期数据库中的所有表
         .schema xxx 列出当前指定的xxx表结构
         .dump user   ===>导出数据库
         重定向
         sqlite3 test.db .dump > 123.sql
         sqlite3 xxx.db < test.sql ===>导入数据库
    2、标准SQL语句:===》通用语法在其他平台可以直接使用。struct query language;
         注意:所有的sql语句都以';'结尾。
         创建一个表:ddl
        create table  表名(表字段1,表字段2,...);
         eg: create table user(id,name,age);                              char (有长度限制)字符串
         注意:以上表的表字段,支持如下数据类型。int           text           real          blob(照片)
               默认是text类型。char;
         create table 表名 (表字段 类型,表字段 类型,。。。。);
         eg:
         create table user(id int  ,name char,age int);
删除一个表:
         drop table  表名;
         eg:drop table user;
        数据库常规操作: 增加 删除 修改 查询
        
向表中增加数据:
       insert into 表名 (字段名称 ) values (值名称);
        eg:insert into user (id,age)    values (1,10);
       insert into user values(3,"wang",11);
        insert into user (age) values ( 12);
 查询表中的数据:
        select 列名 from 表名  条件;
        eg:select * from user ; 查询有多少列
            select id from user;只取某几列:
            select id,name from user where not  age <30
            where name   like '三一'   % _ 通配符 
查询创建的表中是什么类型 : .schema
要是想在查询的列最上面显示类型: .headers on
                                                                                               asc
            select *from user where age>20 or age<50 order by age desc limit 2 ;
            &&  ||


用like 查询通配符,=查看具体哪个re'e
%和_是0到任意多个字符 通配符
  
       修改表中数据:
        update 表名 set 表字段 = 值  满足条件:
        eg: update user set id = 1 where name = 'li';
        update user set id = 1 where name = "li" and passwd = "123";
        update user set id = 2 where name = "li" or  name = "zhao";
     
       
删除表中数据:
        delete from 表名  满足条件:
        eg:delete from user ;  ///删除表中所有数据
               delete from user where id  = 1; ///删除id=1 的数据;
            delete from user where id =1 and name = "zhang";
            delete from user where id = 1 or id  = 2;
          
     >2022-1-1 and <2018-12-31
插入时间列 int int;
     unicode
     CREATE TABLE user1(id int,name char,age int,dt datetime);
、'2022-07-01 19:00:00'
insert into user1 values (2,'张三',23,datetime('now','+8 hours'));

自动增长列
     sqlite> CREATE TABLE user3(id INTEGER PRIMARY KEY ASC,name char,age int,dt datetime);  主键 
 sqlite> insert into user3 (NULL,'李四',23,datetime('now'));   (void*)0
                                        asc 
     where (group by having) order by [desc] limit;
select * from user where id<10 order by id limit 2;
维护命令:
1、数据的导出:
         sqlite3 xxx.db .dump > xxx.sql
     //将数据库名称为xxx的数据库整体导出到脚本中。
    “>”输出重定向
  
2、数据的导入:
         sqlite3 xxx.db < xxx.sql
“<”输出重定向
3、可视化工具安装:s
     sudo apt-get install sqlitebrowser 
     
     
 ==================================================
 sqlite3 数据库编程接口:
1、需要的头文件
         sqlite3.h
2、编译过程
         -lsqlite3
3、编程框架:
 打开数据库 ==》读写数据库(增,删,改,查) ==》关闭数据库
sqlite3.h
3.1 打开数据库: sqlite3_open
     int sqlite3_open(char * path,sqlite3 ** db);
     功能:打开指定path路径+文件名称的数据库,并将
           打开的地址指向db变量的句柄。
     参数:path 要打开的数据库路径+名称
           db  要打开的数据库地址指针
     返回值:成功  0
             失败  -1;

3.2 关闭数据库: sqlite3_close
     int sqlite3_close(sqlite3 *db);
     功能:关闭指定的数据库
     参数:要关闭的数据库地址
     返回值:成功  0
             失败  -1;

3.3 数据库操作:
     查询操作:sqlite3_get_table();  select 
    int sqlite3_get_table(sqlite3 *db,char *sql,
                     char *** rest,int *nrow,int *ncol,
                     char ** errmsg);
    功能:在db数据库上执行sql查询语句,并将执行的
           结果集返回到rest地址上,同时返回查询的行和列。
     参数:db 要执行查询语句的数据库
           sql  要执行的select查询语句
           rest 查询的结果集是一个三级指针
           nrow 查询的结果的行数
           ncol 查询的结果的列数
           errmsg 如果执行有错误,则存储错误。
     返回值:成功 0
             失败 非0;
执行sql语句:sqlite3_exec(); insert delete update
    int sqlite3_exec(sqlite3 *db,char *sql,callback fun,
                     void * arg,char ** errmsg);
    功能:在db数据库上执行sql 非查询语句。
           并将结果返回。
     参数:db 要执行sql的数据库
           sql  要执行的非查询sql语句。
           fun  如果该函数要执行查询语句,则该回调函数
                  用来回收查询的结果。
           arg  回调函数的参数,如果没有回调函数则该参数为NULL;
           errmsg  执行过程中的错误信息。
     返回值:执行成功  0
             失败  非0 ;

    int fun(void *arg ,int f_num,char ** f_value,
             char ** f_name)
     
     功能:该函数用于sqlite3_exec执行select语句的
           结果集返回数据。
     参数:arg 由sqlite3_exec传入的参数
           f_num 执行该命令所返回测结果集的字段个数。
           f_value 查询结果集中的字段的值。
           f_name  查询结果集中的字段的名称。
     返回值:成功 0
             失败 非0
     注意:该回调函数必须有返回值,否则可能导致查询异常。
#include <stdio.h> // 引入标准输入输出库  
#include <stdlib.h> // 引入标准库,用于动态内存分配、程序控制等  
#include <sqlite3.h> // 引入SQLite3库的头文件  
  
int main(int argc, char *argv[])  
{  
    sqlite3* db; // 声明一个指向sqlite3结构体的指针,用于存储数据库连接  
  
    // 尝试打开数据库文件aaa.db,如果文件不存在则创建它  
    // sqlite3_open的第二个参数是指向sqlite3*的指针的地址,用于存储数据库连接  
    int ret = sqlite3_open("aaa.db",&db);  
    if(SQLITE_OK != ret) // 如果打开失败  
    {  
        // 使用sqlite3_errmsg获取错误信息,并打印到标准错误输出  
        fprintf(stderr,"open db error:%s\n",sqlite3_errmsg(db));  
        // 无论成功与否,都需要关闭数据库连接  
        sqlite3_close(db);   
        // 返回错误代码1表示程序异常退出  
        return  1;  
    }  
  
    // 准备要执行的SQL命令,这里是一个插入命令  
    char sql_cmd[256]="insert into user values(8,'zhaosi',12);";  
    // 声明一个用于接收SQL执行后可能产生的错误信息的指针  
    char * errmsg;  
  
    // 执行SQL命令  
    // sqlite3_exec的第四个参数和第五个参数是回调函数和数据指针,这里都不需要,所以设为NULL  
    // 第五个参数是指向错误信息的指针的地址,用于接收可能产生的错误信息  
    ret = sqlite3_exec(db,sql_cmd,NULL,NULL,&errmsg);  
    if(SQLITE_OK != ret) // 如果执行失败  
    {  
        // 打印错误信息到标准错误输出  
        fprintf(stderr,"exec sqlcmd error:%s\n",errmsg);  
        // 使用sqlite3_free释放sqlite3_exec分配的错误信息内存  
        sqlite3_free(errmsg);  
        // 关闭数据库连接  
        sqlite3_close(db);   
        // 返回错误代码1表示程序异常退出  
        return  1;  
    }  
  
    // 如果一切顺利,则关闭数据库连接  
    sqlite3_close(db);  
    // 程序正常退出  
    return 0;  
}
 练习:自己创建一个学生表,最少不能低于3个字段
       最好有一个唯一主键,
       设计程序以代码方式,依次输入5个学生信息
       并存储到数据库中,最终查询显示所有学习信息。
      id(主键,自动),name,age,addr,datetime,recommand;
       
       至少插入5条记录。
       
       修改3处。
       
       删除2条记录。
      
 给数据库表添加主键:
 1、sqliteman 设计表过程中选择 ;PK INTER
 2、SQL 语句:
    create table user(id int primary key,name text);
     
     
     新建表
     create table stu_info(id int ,name char ,age int ,phone char ,email char,qq char);
     
     增加记录
     insert into stu_info values (2,'关二哥',55,'13011112222','gauanerge@163.com','8888888');
     
     查询记录
     select * from stu_info;
     
     修改记录
     
     
     update stu_info set age = 56
     where id = 2;
     
     删除
     delete from stu_info where id = 2;
     
     
     select*from 表明  where
     从句where 
     
     
     (id int,name char,age int,kind int,salary real);
     
     
     insert into person values(9,'周瑜',39,3,3638.20);

ldd查看使用了哪些库
,该代码段使用SQLite3库来查询并打印user表中的数据、
#include <stdio.h> // 引入标准输入输出库  
#include <stdlib.h> // 引入标准库(虽然在这段代码中未直接使用,但通常是C程序的标准包含之一)  
#include <sqlite3.h> // 引入SQLite3库的头文件  
  
// 定义一个回调函数,用于处理sqlite3_exec查询结果的每一行  
// 参数arg是传递给sqlite3_exec的第四个参数(这里未使用,设为NULL)  
// col是结果集中的列数  
// result是一个指向字符串数组的指针,每个字符串都是结果集中的一列  
// title是一个指向列名数组的指针(注意:在某些版本的SQLite中,title可能不是所有情况下都可用)  
int show(void* arg, int col, char** result, char** title) {  
    int i = 0;  
    static int flag = 0; // 静态变量,用于控制列标题只打印一次  
    if (0 == flag) {  
        // 打印列标题(如果存在的话)  
        // 注意:title在某些版本的SQLite或某些配置下可能不是有效的,具体取决于编译的SQLite版本和设置  
        for (i = 0; i < col; i++) {  
            if (title && title[i]) { // 检查title是否为NULL以及当前列名是否为NULL  
                printf("%s\t", title[i]);  
            } else {  
                // 如果title不可用,可以选择不打印标题或使用占位符  
                printf("Column%d\t", i + 1);  
            }  
        }  
        printf("\n");  
        flag = 1; // 设置标志位,避免重复打印标题  
    }  
    // 打印结果集的每一行数据  
    for (i = 0; i < col; i++) {  
        printf("%s\t", result[i] ? result[i] : "NULL"); // 如果结果为NULL,则打印"NULL"  
    }  
    printf("\n");  
    return 0; // 回调函数返回0表示成功  
}  
  
int main(int argc, char *argv[]) {  
    sqlite3* db; // 声明一个指向sqlite3结构体的指针,用于存储数据库连接  
    int ret = sqlite3_open("aaa.db", &db); // 尝试打开数据库文件aaa.db  
    if (SQLITE_OK != ret) { // 如果打开失败  
        fprintf(stderr, "open db error:%s\n", sqlite3_errmsg(db)); // 打印错误信息  
        sqlite3_close(db); // 关闭数据库连接(尽管在错误情况下这可能不是必须的,但是一个好习惯)  
        return 1; // 返回错误代码1表示程序异常退出  
    }  
    char sql_cmd[256] = "select * from user;"; // 准备SQL查询命令  
    char *errmsg; // 声明一个用于接收SQL执行后可能产生的错误信息的指针  
    ret = sqlite3_exec(db, sql_cmd, show, NULL, &errmsg); // 执行SQL查询,并注册回调函数show来处理结果  
    if (SQLITE_OK != ret) { // 如果执行失败  
        fprintf(stderr, "exec sqlcmd error:%s\n", errmsg); // 打印错误信息  
        sqlite3_free(errmsg); // 释放sqlite3_exec分配的错误信息内存  
        sqlite3_close(db); // 关闭数据库连接  
        return 1; // 返回错误代码1表示程序异常退出  
    }  
    sqlite3_close(db); // 正常情况下也关闭数据库连接  
    return 0; // 程序正常退出  
}在C语言中使用SQLite3库来查询数据库并打印结果
#include <stdio.h>  
#include <stdlib.h>  
#include <sqlite3.h>  
  
// 回调函数,用于处理查询结果的每一行  
int show(void* arg, int col, char** result, char** title) {  
    int i = 0;  
    static int flag = 0; // 静态变量,用于控制列标题只打印一次  
    if (0 == flag) {  
        // 如果flag为0,则打印列标题  
        for (i = 0; i < col; i++) {  
            // 注意:title可能为NULL或包含空字符串,这里直接打印  
            printf("%s\t", title ? title[i] : "Column?");  
        }  
        printf("\n");  
        flag = 1; // 设置flag为1,避免再次打印列标题  
    }  
    // 打印当前行的数据  
    for (i = 0; i < col; i++) {  
        // 注意:result[i]也可能为NULL,这里直接打印(如果为NULL,则打印空字符串)  
        printf("%s\t", result[i] ? result[i] : "");  
    }  
    printf("\n");  
    return 0; // 回调函数返回0表示成功  
}  
  
int main(int argc, char *argv[]) {  
    sqlite3* db; // 指向SQLite数据库连接的指针  
    int ret = sqlite3_open("aaa.db", &db); // 尝试打开数据库  
    if (SQLITE_OK != ret) { // 如果打开失败  
        // 打印错误信息并关闭数据库(尽管在错误情况下关闭可能不是必需的,但这是一个好习惯)  
        fprintf(stderr, "open db error:%s\n", sqlite3_errmsg(db));  
        sqlite3_close(db);  
        return 1; // 返回错误代码  
    }  
    char sql_cmd[256] = "select * from user;"; // 准备SQL查询语句  
    char *errmsg; // 用于接收可能的错误信息的指针  
    ret = sqlite3_exec(db, sql_cmd, show, NULL, &errmsg); // 执行SQL查询并注册回调函数  
    if (SQLITE_OK != ret) { // 如果执行失败  
        // 打印错误信息,释放错误信息占用的内存,并关闭数据库  
        fprintf(stderr, "exec sqlcmd error:%s\n", errmsg);  
        sqlite3_free(errmsg);  
        sqlite3_close(db);  
        return 1; // 返回错误代码  
    }  
    // 查询成功完成,关闭数据库连接  
    sqlite3_close(db);  
    return 0; // 程序正常退出  
}


















