c++ - C++ MySql 连接器 - 查询超出范围的结果
问题描述
我遇到了 C++ mysql 连接器查询执行结果的范围问题。
在下面的代码中,ResultSet *
结果最初是从另一个函数传递的NULL
;但是,执行完这条线后result = statement->executeQuery( query )
,结果不再是NULL
.
表格中也没有打印错误。
从该函数返回时会出现问题。结果ResultSet *
从不NULL
等于NULL
。
显然,对 sql 查询结果有某种形式的作用域。也许他们的函数正在返回对局部变量的引用(否则真的不确定)?
我如何解决这个范围问题,以便调用此函数的类/函数可以随意处理结果并减轻在此包装器中编写一堆专用函数的需要?此外,应尽量减少副本 - 因此使用指针。
bool MySQLConnector::ExecuteQuery( std::string query, sql::ResultSet * result )
{
//connection is a member variable and has been initialized
sql::Statement * statement = connection->createStatement();
try
{
result = statement->executeQuery( query );
}
catch( sql::SQLException &e )
{
//handle errors
}
delete statement;
if( result == NULL )
{
printf( "Result is null File: %s Line %i\n", __FILE__, __LINE__ );
return false;
}
else
{
printf("Result is not null File: %s Line %i\n", __FILE__, __LINE__ );
}
return true;
}
如果我有一个foo
使用正确参数调用上述函数的函数。printf
将打印结果不是 null的声明,但是在foo
执行之后ExecuteQuery
,传递给函数的指针变为NULL
。
解决方案
有几个问题:
1.result
按值传递
你按价值传递result
。这意味着该函数接收您在调用该方法时传递的指针的副本。
例如,如果调用的代码ExecuteQuery
如下所示:
std::string query("SELECT ...");
sql::ResultSet *result = NULL;
ExecuteQuery(query, result);
然后ExecuteQuery
无法更改 的值result
,因为它已复制到方法中。如果你想改变它的值,你应该传递一个对结果的引用。您可以通过更改ExecuteQuery
为:
bool MySQLConnector::ExecuteQuery( std::string query, sql::ResultSet *& result )
然后,ExecuteQuery
操作原始指针,而不是副本。
2. MySQL C++ API 在删除ResultSet
时释放Statement
就像@nos 指出的那样,当您调用时delete statement
,您还释放了保存您的信息的资源result
。
result
仍然会有一个有效的值,因为它不会知道释放的内存,但是如果你访问它,它可能会导致分段错误。
处理此问题的正确方法是:
- 复制结果
- 或者
- 让调用者也传递一个语句对象,并在使用结果中的值后释放它。
推荐阅读
- python - 无法通过套接字发送字节:消息太长
- azure - 您如何使用代码验证逻辑应用程序 microsoft.web/connections 连接
- python - 从多索引问题中去除空格 - 我的代码还删除了索引名称
- python - If the user inputs a position over 5. It is supposed to print `The account number not found`
- kubernetes - Kubernetes 无法访问从节点的 pod
- node.js - 如何在 gulp 任务上创建一个空文件?
- mysql - 当我尝试查询数据数组时,节点中的 MariaDB SQL 抛出 ER_PARSE_ERROR
- c - 使用 printf 在 yacc 中打印字符串文字标记会导致分段错误
- excel - VBA查找方法不返回实际上存在于工作表中的值
- javascript - 使用来自 aysnc Javascript http 请求的数据?(AWS 无服务器)