MySQL Connector/C++常见接口/类介绍
当我们有用C++程序连接MySQL数据库并执行SQL语句时,往往要用到相关的库,这里使用的是MySQL官方提供的Connector/C++库,为了更好地使用库里的内容,我们先来熟悉一下里面常用的接口和类
MySQL准备
为了便于测试,我们专门创建一个用于测试的用户和数据库,并给予相关权限
1 | create user 'conn'@'localhost' identified by '12345678'; |
认识接口/类
我们将逐个介绍如下类及其相关接口
sql::SQLStringsql::mysql::MySQL_Driver–<mysql_driver.h>sql::mysql::get_mysql_driver_instance()
sql::Connection–<mysql_connection.h>sql::Statement–<cppconn/statement.h>sql::ResultSet–<cppconn/resultset.h>sql::SQLException–<cppconn/exception.h>
sql::SQLString
从名字就能看出,这是SQL语言所用的字符串类。主要用于对SQL语句的字符串操作。我们来看看它的特点
构造函数的支持
1 | //访问限定符是博客作者手动加的,与源码的位置和数量略有差异 |
可以看到SQLString的构造已经支持了常用的字符串结构,尤其是std::string和C语言字符串
接下来我们看看它的其它比较特别的接口
隐式类型转换重载
1 | public: |
这种类型的重载函数可能比较少见,但是它出现于C++98,且在后续版本没有改变,都是支持的。
它的效果是为自定义类型提供了自定义的隐式类型转换。有了上述代码的重载后,sql::SQLString就支持了以下写法
1 | sql::SQLString sql_str("这原本是一条SQLString类型的字符串!"); |
字符串比较函数
首先是严格比较的函数
1 | public: |
这三个比较函数会对两个字符串进行严格的大小比较,唯一的区别就是传参不同,后续统一以SQLString为例介绍字符串相关的操作,但是要知道它也支持另外两种类型的字符串
接下来介绍不严格比较(忽略大小写)
1 | public: |
可以看到这个函数拷贝了两个字符串,并全都统一转换成了小写,这样就可以忽略大小写进行比较了
重载流插入
1 | namespace std |
可以看到它直接支持流插入。
sql::mysql::MySQL_Driver
来自头文件<mysql_driver.h>
这是一种MySQL 驱动程序类,它主要用于创建连接对象来连接数据库并返回sql::Connection*,在代码上就是实例化出了一个对象并返回它的指针。
至于获取driver实例,可以通过命名空间内提供的全局函数获取: sql::mysql::get_mysql_driver_instance();。这个函数会返回一个sql::mysql::MySQL_Driver *指针
示例如下
1 | sql::mysql::MySQL_Driver *driver;//声明指针 |
主要用途:这个对象提供了一个connect()方法来创建连接对象并连接到数据库,参数要先后提供ip地址,用户名,用户密码
sql::Connection * connect(const sql::SQLString& hostName, const sql::SQLString& userName, const sql::SQLString& password);
创建连接
1 | std::unique_ptr<sql::Connection> con(driver->connect("tcp://127.0.0.1:3306", "conn", "12345678")); |
sql::Connection
sql::Connection这个类用于表示与数据库的连接,提供了多种方法来执行 SQL 查询、管理事务、以及处理与数据库交互的各种操作。以下是关于 sql::Connection 的一些关键点
基本功能
- 连接管理:
sql::Connection负责管理与数据库的连接,包括建立和关闭连接。 - 执行查询: 通过该类,可以执行
SQL语句(如SELECT、INSERT、UPDATE和DELETE)。 - 事务控制: 支持事务处理,可以开始、提交和回滚事务。
主要成员函数
setSchema: 设置数据库,传入名称即可,无返回值reconnect: 用于以相同的连接参数重连createStatement: 创建一个用于执行 SQL 语句的sql::Statement对象。并返回一个sql::Statement*指针prepareStatement: 创建一个用于执行预处理 SQL 语句的sql::PreparedStatement对象。并返回一个sql::PreparedStatement*指针setAutoCommit: 设置是否自动提交事务。传入一个bool类型的参数commit: 提交当前事务的更改。setSavepoint: 创建存档点。会产生一个sql::Savepoint对象并返回一个sql::Savepoint*指针- 有两种重载,可以不传参,也可以传字符串作为存档点的名称
rollback: 回滚当前事务的更改。- 有两种重载,可以不传参,也可以传入
sql::Savepoint*指针,回滚到存档点
- 有两种重载,可以不传参,也可以传入
close: 关闭与数据库的连接。
这里只使演示一下createStatement获取sql::Statement*用于后文使用
1 | std::unique_ptr<sql::Statement> stmt(con->createStatement()); |
sql::Statement
注:必须包含头文件#include <cppconn/statement.h>
主要用于执行静态 SQL 语句,通过调用成员函数,并传入一个字符串
主要方法如下
execute: 返回值为bool类型,可以执行任意类型的SQL语句,如SELECT、INSERT、UPDATE和DELETE。如果执行的是查询语句,则返回true;如果执行的是更新语句,则返回false。executeQuery: 专门用于执行查询语句(如SELECT),并返回一个sql::ResultSet对象的指针。executeUpdate: 专门用于执行更新语句(如INSERT、UPDATE和DELETE),并返回受影响的行数。返回值为int类型getConnection: 返回创建这个sql::Statement的sql::Connection对象。close: 关闭sql::Statement,释放其占用的资源。
这里写一个获取查询结果的示例代码
1 | std::unique_ptr<sql::Statement> stmt(con->createStatement()); |
sql::ResultSet
它用于处理 SQL 查询返回的结果集,行为上可以认为它是个单向迭代器,一次只指向查询结果的某一行
主要接口有:
next:bool next()- 将游标从当前位置向前移动一行。如果新的当前行有效,则返回
true;如果没有更多的行,则返回false。
getString:SQLString getString(uint32_t columnIndex) const每一列从1开始SQLString getString(const sql::SQLString& columnLabel) const- 下面的两种get方法均有两种重载
- 获取当前行指定列的 std::string 值。
getInt: 获取当前行指定列的 int 值。 每一列从1开始getDouble: 获取当前行指定列的 double 值。 每一列从1开始getRowsize_t getRow() const- 获取行号,从
1开始
getMetaData:ResultSetMetaData * getMetaData() const- 返回一个
sql::ResultSetMetaData对象指针,包含结果集的元数据信息。
close: 关闭 sql::ResultSet,释放其占用的资源
如果要遍历所有行,只需要像使用迭代器一样使用sql::ResultSet即可。示例如下:
1 | while (res->next()) { |
这里再简单介绍一下getMetaData获得的ResultSetMetaData对象提供了哪些接口,可以获得哪些信息
注意⚠️,不能用智能指针储存sql:ResultSetMetaData*指针,因为它的析构函数是portected的,由别的对象自动释放,而智能指针没有权限自动释放。
它的源码及本文作者注释如下:
1 | namespace sql |
sql::SQLException
用于表示在执行 SQL 操作时发生的异常。这个类继承自标准 C++ 异常类std::runtime_error,因此它可以被 try-catch 块捕获并处理
常用方法
getMessage: 返回异常的详细描述信息。getSQLState: 返回SQL标准的状态码(通常是一个五字符的字符串)。getErrorCode: 返回数据库特有的错误代码。
下面是一个简单示例
1 |
|