`mysql_query()` 数据库查询函数
1) 函数的概念与用途
mysql_query()
是 MySQL C API 中的核心函数,用于向 MySQL 服务器发送 SQL 查询语句。这个函数充当了 C/C++ 应用程序与 MySQL 数据库之间的桥梁,允许程序执行各种数据库操作。
可以将 mysql_query()
想象成一个"数据库信使":你给它一个 SQL 查询指令,它就把这个指令传递给 MySQL 服务器,然后带回执行结果。无论是数据查询、插入、更新还是删除,都需要通过这个函数来执行。
典型应用场景包括:
- 数据检索:执行 SELECT 语句查询数据库中的数据
- 数据操作:执行 INSERT、UPDATE、DELETE 语句修改数据
- 数据库管理:执行 CREATE、ALTER、DROP 等DDL语句
- 事务控制:执行 BEGIN、COMMIT、ROLLBACK 等事务操作
- 存储过程调用:执行 CALL 语句调用存储过程
2) 函数的声明与出处
mysql_query()
是 MySQL C API 的一部分,声明在 mysql.h
头文件中。
#include <mysql.h>int mysql_query(MYSQL *mysql, const char *stmt_str);
要使用这个函数,需要链接 MySQL 客户端库(libmysqlclient
)。
3) 参数详解:连接对象和SQL语句
-
MYSQL *mysql
- 作用:指向 MySQL 连接句柄的指针,由
mysql_init()
和mysql_real_connect()
创建 - 要求:必须是有效的、已连接的数据库连接句柄
- 作用:指向 MySQL 连接句柄的指针,由
-
const char *stmt_str
- 作用:要执行的 SQL 查询语句,以空字符结尾的 C 字符串
- 要求:必须是有效的 SQL 语句,不应包含分号结尾(除非在多个语句中)
- 注意:SQL 语句中不应包含二进制数据(对于二进制数据应使用
mysql_real_query()
)
4) 返回值:执行状态
-
返回值类型:
int
-
返回值含义:
- 成功:返回 0
- 失败:返回非零值
-
错误处理:
- 失败时可以使用
mysql_error()
和mysql_errno()
获取错误信息 - 成功执行 SELECT 查询后,需要使用
mysql_store_result()
或mysql_use_result()
获取结果集
- 失败时可以使用
5) 实战演示:多种使用场景
示例 1:基础查询操作
#include <stdio.h>
#include <mysql.h>int main() {MYSQL *conn;MYSQL_RES *res;MYSQL_ROW row;// 初始化连接conn = mysql_init(NULL);if (conn == NULL) {fprintf(stderr, "mysql_init() failed\n");return 1;}// 连接到数据库if (mysql_real_connect(conn, "localhost", "user", "password", "database", 0, NULL, 0) == NULL) {fprintf(stderr, "Connection failed: %s\n", mysql_error(conn));mysql_close(conn);return 1;}// 执行查询if (mysql_query(conn, "SELECT id, name, email FROM users")) {fprintf(stderr, "Query failed: %s\n", mysql_error(conn));mysql_close(conn);return 1;}// 获取结果集res = mysql_store_result(conn);if (res == NULL) {fprintf(stderr, "Store result failed: %s\n", mysql_error(conn));mysql_close(conn);return 1;}// 处理结果printf("ID\tName\tEmail\n");while ((row = mysql_fetch_row(res)) != NULL) {printf("%s\t%s\t%s\n", row[0], row[1], row[2]);}// 清理资源mysql_free_result(res);mysql_close(conn);return 0;
}
示例 2:数据插入操作
#include <stdio.h>
#include <mysql.h>int main() {MYSQL *conn;// 初始化并连接数据库(省略错误检查简化代码)conn = mysql_init(NULL);mysql_real_connect(conn, "localhost", "user", "password", "testdb", 0, NULL, 0);// 插入数据if (mysql_query(conn, "INSERT INTO users (name, email) VALUES ('John Doe', 'john@example.com')")) {fprintf(stderr, "Insert failed: %s\n", mysql_error(conn));} else {printf("Insert successful, affected rows: %lld\n", mysql_affected_rows(conn));}mysql_close(conn);return 0;
}
示例 3:事务处理
#include <stdio.h>
#include <mysql.h>int main() {MYSQL *conn;conn = mysql_init(NULL);mysql_real_connect(conn, "localhost", "user", "password", "testdb", 0, NULL, 0);// 开始事务mysql_query(conn, "START TRANSACTION");// 执行多个操作if (mysql_query(conn, "UPDATE accounts SET balance = balance - 100 WHERE id = 1")) {mysql_query(conn, "ROLLBACK");fprintf(stderr, "Transfer failed\n");} else if (mysql_query(conn, "UPDATE accounts SET balance = balance + 100 WHERE id = 2")) {mysql_query(conn, "ROLLBACK");fprintf(stderr, "Transfer failed\n");} else {mysql_query(conn, "COMMIT");printf("Transfer successful\n");}mysql_close(conn);return 0;
}
6) 编译方式与注意事项
编译命令:
gcc -o mysql_demo mysql_demo.c $(mysql_config --cflags) $(mysql_config --libs)
或者显式指定路径:
gcc -o mysql_demo mysql_demo.c -I/usr/include/mysql -L/usr/lib/mysql -lmysqlclient
关键注意事项:
- SQL注入风险:不要直接将用户输入拼接到SQL语句中,使用参数化查询或转义函数
- 错误处理:始终检查每个MySQL API调用的返回值
- 资源清理:确保释放所有分配的资源(结果集、连接等)
- 二进制数据:对于包含二进制数据的查询,使用
mysql_real_query()
代替 - 多语句查询:默认情况下,MySQL不允许在单个查询中执行多个语句(出于安全考虑)
- 性能考虑:对于大量数据的检索,考虑使用
mysql_use_result()
而不是mysql_store_result()
7) 执行结果说明
示例 1 可能输出:
ID Name Email
1 Alice alice@example.com
2 Bob bob@example.com
3 Charlie charlie@example.com
展示了如何执行SELECT查询并处理结果集。
示例 2 可能输出:
Insert successful, affected rows: 1
显示了插入操作的成功执行,并获取受影响的行数。
示例 3 可能输出:
Transfer successful
演示了如何使用事务确保多个操作的原子性。
8) 总结:mysql_query()
的工作流程与价值
mysql_query()
的工作流程可以总结如下:
mysql_query()
是 MySQL C API 的核心函数,它的价值在于:
- 数据库交互:提供了C/C++程序与MySQL数据库交互的主要手段
- 灵活性:支持执行各种类型的SQL语句
- 简单易用:接口简单,易于理解和使用
最佳实践建议:
- 使用预处理语句:对于用户输入的数据,使用预处理语句防止SQL注入
- 彻底的错误处理:检查每个数据库操作的返回值
- 资源管理:确保正确释放所有数据库资源
- 连接复用**:在可能的情况下复用数据库连接,避免频繁连接断开
- 安全考虑:不要在代码中硬编码数据库凭据,使用安全配置方式
mysql_query()
虽然简单,但却是 MySQL C API 编程的基础。掌握它的正确用法和注意事项,对于开发稳定、安全的数据库应用程序至关重要。无论是简单的数据查询还是复杂的事务处理,mysql_query()
都是连接C/C++应用与MySQL数据库的重要桥梁。