C++中访问const unsigned char数组后续输出乱码问题求助
问题:SQLite查询结果循环内正常输出,后续访问数组出现乱码
我正在为学校编写一个带简单登录界面的C++程序,目前仍在学习阶段。在以下代码片段中遇到一个奇怪的问题:循环内部可以正常输出用户名、密码和姓名,但后续访问数组时却输出乱码。
sql = "SELECT username,password,real_name from Users"; const unsigned char* usernames[20]; // 20 max usernames const unsigned char* passwords[20]; const unsigned char* names[20]; rc = sqlite3_prepare_v2(db, sql, -1, &stmt, NULL); //sqlite3_exec(db, sql, callback, usernames, &zErrMsg); if( rc != SQLITE_OK ) { printf("error: %s ", sqlite3_errmsg(db)); return 1; } int i = 0; while ((rc = sqlite3_step(stmt)) == SQLITE_ROW) { usernames[i]= sqlite3_column_text (stmt, 0); passwords[i] = sqlite3_column_text(stmt, 1); names[i] = sqlite3_column_text(stmt, 2); // 这里输出正常 cout << usernames[i] << ":" << passwords[i] << ":" << names[i] << "\n"; i = i + 1 ; } // 这里输出乱码 cout << usernames[0];
解决方法
感谢大家!你们的建议帮助我解决了问题。我需要使用strdup,它不是标准C函数,但实现起来非常简单,只需自行实现即可!
问题根源
sqlite3_column_text()返回的指针指向SQLite内部维护的临时缓冲区,当sqlite3_step()推进到下一行,或者查询结束后,这个缓冲区的内容会被覆盖或释放。循环中保存的只是指针,并非字符串内容,所以循环结束后再访问这些指针,读取到的就是无效数据,表现为乱码。
修正后的代码示例
需要把查询到的字符串内容复制到自己管理的内存中,strdup可以完成分配内存+复制字符串的操作,修改后的循环部分代码:
int i = 0; while ((rc = sqlite3_step(stmt)) == SQLITE_ROW) { // 将SQLite缓冲区的内容复制到自己的内存 usernames[i] = reinterpret_cast<const unsigned char*>( strdup(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0))) ); passwords[i] = reinterpret_cast<const unsigned char*>( strdup(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1))) ); names[i] = reinterpret_cast<const unsigned char*>( strdup(reinterpret_cast<const char*>(sqlite3_column_text(stmt, 2))) ); cout << usernames[i] << ":" << passwords[i] << ":" << names[i] << "\n"; i++; }
注意事项
- 使用
strdup分配的内存需要在不再使用时调用free()释放,避免内存泄漏。 - 如果不想依赖非标准的
strdup,可以手动实现一个:
char* my_strdup(const char* s) { if (!s) return nullptr; size_t len = strlen(s) + 1; char* result = static_cast<char*>(malloc(len)); if (result) { strcpy(result, s); } return result; }
之后用my_strdup代替strdup即可。
内容的提问来源于stack exchange,提问作者user14745176
相关产品推荐
相关产品推荐

