C语言连接数据库

来源:互联网 发布:淘宝客服兼职 招聘找 编辑:程序博客网 时间:2024/05/16 13:57

MySQL是Linux系统下广泛使用的开源免费数据库,是Linux应用程序数据存储的首选。许多发布的Linux版本是自带MySQL的,但是也有些发布版本是不带的(比如我现在用的Ubuntu),那就需要手动安装。在Synaptic Packet Management中搜索“mysql”,可以找到“mysql-client"包,点击安装即可。


安装好的MySQL是在命令行下运行的,这对于许多经常在Windows下开发程序,习惯使用图形化工具的人来说是很痛苦的。因此我们需要 安装MySQL图形化管理工具MySQL Administrator和MySQL Query Brower。打开Ubuntu Software Center,输入”mysql"搜索,可以看到这两个工具,点击安装即可。


安装了以上的软件包后,我们可以正常使用MySQL完成数据管理工作,但是很多时候我们需要通过编写程序访问MySQL。此时,在程序中需要加载MySQL驱动头文件,但是默认这些驱动包是没有安装的,因此我们需要在Synaptic Packet Management中找到"libmysqld-dev"包并安装。


用C语言连接MySQL数据库有两个步骤

1)初始化一个连接句柄结构

2)建立连接

所用到的函数如下:

[cpp] view plaincopyprint?
  1. #include <mysql.h>  
  2. MYSQL *mysql_init(MYSQL *); // 初始化连接句柄  
  3. MYSQL *mysql_real_connect(MYSQL *connection,   
  4.                           const char *server_host,                          
  5.                           const char *sql_user_name,  
  6.                           const char *sql_password,   
  7.                           const char *db_name,   
  8.                           unsigned int port_number,   
  9.                           const char *unix_socket_name,   
  10.                           unsigned int flags); //建立连接  
  11. void mysql_close(MYSQL *connection); //关闭连接  
  12. int mysql_options(MYSQL *connection, enum option_to_set, const char *argument); //设置连接选项  
  13. option_to_set的值为下列三个值之一:  
  14. MySQL_OPT_CONNECT_TIMEOUT  //连接超时前的等待秒数  
  15. MySQL_OPT_COMPRESS //网络连接中使用压缩机制  
  16. MySQL_INIT_COMMAND //每次建立连接后发送的命令  
使用上面函数实现MySQL数据库连接的程序如下:

[cpp] view plaincopyprint?
  1. /* 
  2.  * gcc -I/usr/include/mysql connect1.c -L/usr/lib/mysql -lmysqlclient -o connect1 
  3.  */  
  4. #include <stdlib.h>  
  5. #include <stdio.h>  
  6.   
  7. #include <mysql.h>  
  8.   
  9. int main()  
  10. {  
  11.     MYSQL *conn_ptr;  // 定义连接句柄  
  12.   
  13.     conn_ptr = mysql_init(NULL); // 初始化连接句柄  
  14.     if(!conn_ptr)  
  15.     {  
  16.         fprintf(stderr, "mysql_init falied\n");  
  17.         return EXIT_FAILURE;  
  18.     }  
  19.   
  20.     // 建立连接  
  21.     conn_ptr = mysql_real_connect(conn_ptr, "localhost""root""pwd""test", 0, NULL, 0);  
  22.     if(conn_ptr)  
  23.     {  
  24.         printf("Connection success\n");  
  25.     }  
  26.     else  
  27.     {  
  28.         printf("Connection failed\n");  
  29.     }  
  30.   
  31.     // 关闭连接  
  32.     mysql_close(conn_ptr);  
  33.   
  34.     return EXIT_SUCCESS;  
  35. }  
程序编译运行后显示“Connection success"表明程序已经成功与MySQL数据库建立连接,并在程序结束前关闭连接。

上面的程序是在假设没有错误的情况下运行,如果数据库连接过程中出现了错误,我们就需要以下两个函数来处理错误信息:

[cpp] view plaincopyprint?
  1. unsigned int mysql_errno(MYSQL *connection); //返回错误代码(非零值)  
  2. char *mysql_error(MYSQL *connection); //返回错误信息  
具体使用方法如下:
[cpp] view plaincopyprint?
  1. /* 
  2.  * gcc -I/usr/include/mysql connect2.c -L/usr/lib/mysql -lmysqlclient -o connect2 
  3.  */  
  4. #include <stdlib.h>  
  5. #include <stdio.h>  
  6. #include <mysql.h>  
  7.   
  8. int main(int argc, char *argv[])  
  9. {  
  10.     MYSQL connection;  
  11.     mysql_init(&connection); //初始化连接  
  12.     if(mysql_real_connect(&connection, "localhost""root""unknown""test", 0, NULL, 0)) //建立连接  
  13.     {  
  14.         printf("Connection success\n");  
  15.         mysql_close(&connection);  
  16.     }  
  17.     else //连接失败打印错误信息  
  18.     {  
  19.         fprintf(stderr, "Connection failed\n");  
  20.         if(mysql_errno(&connection))  
  21.         {  
  22.             fprintf(stderr, "Connection error %d: %s\n", mysql_errno(&connection), mysql_error(&connection));  
  23.         }  
  24.     }  
  25.   
  26.     return EXIT_SUCCESS;  
  27. }  
运行上述程序,如果MySQL的登陆密码不是unknown则打印错误信息(拒绝访问——Access denied)。

程序访问数据库不只是与数据库建立连接,更重要的是通过SQL语句的执行查询或改变数据库中数据。执行SQL语句可以通过下列函数实现。
[cpp] view plaincopyprint?
  1. //执行SQL语句,成功返回0  
  2. int mysql_query(MYSQL *connection, const char *query);  


SQL语句分为两类,返回数据的SQL(SELECT)和不返回数据的SQL(UPDATE、DELETE、INSERT)。

1)不返回数据的SQL
[cpp] view plaincopyprint?
  1. // 返回查询受影响的行  
  2. my_ulong mysql_affected_rows(MYSQL *connection);  


对一段SQL语句执行后可以通过调用此函数查看SQL语句执行后,数据库中数据状态改变的行数,以此判断SQL的执行成功与否。

[cpp] view plaincopyprint?
  1. /* 
  2.  * gcc -I/usr/include/mysql insert1.c -L/usr/lib/mysql -lmysqlclient -o insert1 
  3.  */  
  4. #include <stdlib.h>  
  5. #include <stdio.h>  
  6. #include <mysql.h>  
  7.   
  8. int main(int argc, char *argv[])  
  9. {  
  10.     int res;  
  11.     MYSQL connection;  
  12.   
  13.     mysql_init(&connection);  
  14.     if(mysql_real_connect(&connection, "localhost""root""pwd""test", 0, NULL, 0))  
  15.     {  
  16.         printf("Connection success\n");  
  17.   
  18.         res = mysql_query(&connection, "INSERT INTO children(fname, age) VALUES('ann', 3)");  
  19.   
  20.         if(!res)  
  21.         {  
  22.             printf("Inserted %lu rows\n", (unsigned long)mysql_affected_rows(&connection)); //打印受影响的行数  
  23.         }  
  24.         else  
  25.         {  
  26.             fprintf(stderr, "Insert error %d: %s\n", mysql_errno(&connection), mysql_error(&connection));  
  27.         }  
  28.   
  29.         mysql_close(&connection);  
  30.     }  
  31.     else  
  32.     {  
  33.         fprintf(stderr, "Connection failed\n");  
  34.         if(mysql_errno(&connection))  
  35.         {  
  36.             fprintf(stderr, "Connection error %d: %s\n", mysql_errno(&connection), mysql_error(&connection));  
  37.         }  
  38.     }  
  39.   
  40.     return EXIT_SUCCESS;  
  41. }  


2)返回数据的SQL

返回数据的SQL是指通过查询语句从数据库中取出满足条件的数据记录。
[cpp] view plaincopyprint?
  1. //一次提取所有数据  
  2. MYSQL_RES *mysql_store_result(MYSQL *connection);  
  3. //一次提取一行数据  
  4. MYSQL_RES *mysql_use_result(MYSQL *connection);  
  5. //清除结果集对象  
  6. void mysql_free_result(MYSQL_RES *result);  
使用方法如下所示:

[cpp] view plaincopyprint?
  1. #include <stdlib.h>  
  2. #include <stdio.h>  
  3. #include <mysql.h>  
  4.   
  5. MYSQL connection;  
  6. MYSQL_RES *sqlres;  
  7. MYSQL_ROW sqlrow;  
  8.   
  9. int main(int argc, char *argv[])  
  10. {  
  11.     int res;  
  12.   
  13.     mysql_init(&connection);  
  14.   
  15.     if(mysql_real_connect(&connection, "localhost""root""pwd""mysql", 0, NULL, 0))  
  16.     {  
  17.         printf("Connection success\n");  
  18.         res = mysql_query(&connection, "SELECT user, password, host from user");  
  19.         if(res)  
  20.         {  
  21.             printf("SELECT error: %s\n", mysql_error(&connection));  
  22.         }  
  23.         else  
  24.         {  
  25.             // 一次取全部数据  
  26.             sqlres = mysql_store_result(&connection);  
  27.             if(sqlres)  
  28.             {  
  29.                 printf("Retrieved %lu rows\n", (unsigned long)mysql_num_rows(sqlres));  
  30.                 while((sqlrow = mysql_fetch_row(sqlres)))  
  31.                 {  
  32.                     printf("Fetched data...\n");  
  33.                 }  
  34.                 if(mysql_errno(&connection))  
  35.                 {  
  36.                     fprintf(stderr, "Retrive error: %s\n", mysql_error(&connection));  
  37.                 }  
  38.   
  39.                 mysql_free_result(sqlres);  
  40.             }  
  41.   
  42.             // 一次取一行数据  
  43.             /*sqlres = mysql_use_result(&connection); 
  44.             if(sqlres) 
  45.             { 
  46.                 while((sqlrow = mysql_fetch_row(sqlres))) 
  47.                 { 
  48.                     printf("Fetched data...\n"); 
  49.                 } 
  50.                 if(mysql_errno(&connection)) 
  51.                 { 
  52.                     printf("Retrive error: %s\n", mysql_error(&connection)); 
  53.                 } 
  54.                 mysql_free_result(sqlres); 
  55.             }*/  
  56.         }  
  57.         mysql_close(&connection);  
  58.     }  
  59.     else  
  60.     {  
  61.         fprintf(stderr, "Connection failed\n");  
  62.         if(mysql_errno(&connection))  
  63.         {  
  64.             fprintf(stderr, "Connection error %d: %s\n", mysql_errno(&connection), mysql_error(&connection));  
  65.         }  
  66.     }  
  67.   
  68.     return EXIT_SUCCESS;  
  69. }  
一次取全部数据增加了网络负载,但是可以保证数据的完整性。一次取一行数据平衡了网络负载,减小了数据开销,但是增加了时延,因为每次取数据都必须通过网络。


最后一个比较重要的功能是对数据集中的数据进行处理,可能通过列号或者列名来读取数据。

[cpp] view plaincopyprint?
  1. //返回结果集中的字段数目  
  2. unsigned int mysql_field_count(MYSQL *connection);  
  3.   
  4. MYSQL_FIELD *mysql_fetch_field(MYSQL_RES *result);  
[cpp] view plaincopyprint?
  1. void display_row()  
  2. {  
  3.     unsigned int field_count;  
  4.     field_count = 0;  
  5.     while(field_count < mysql_field_count(&connection))  
  6.     {  
  7.         printf("%s ", sqlrow[field_count]);  
  8.         field_count++;  
  9.     }  
  10.     printf("\n");  
  11. }  


小结:通过以上分析,可以了解在Linux操作系统环境下如何通过程序建立与MySQL数据的连接,并且通过库函数的调用可以实现对数据库的增删改查操作,在出现错误时,通过函数调用可以返回错误代码,也可以直接返回错误信息。

0 0
原创粉丝点击