今天写项目时(在与elastisearch服务端的交互模块),遇到一个裸指针和智能指针指向同一块空间,导致段错误Segmentation fault,特此记录。
//error code
#include "es.hh"
int main()
{
// 创建es客户端,与es建立连接
try
{
elasticlient::Client* client = new elasticlient::Client({"http://localhost:9200/"});
// 创建索引
EsIndex es_index(client, "user", "_doc");
es_index.append("nickname", "text", "ik_maxword", true);
es_index.append("user_id", "keyword", "standard");
es_index.append("phone", "keyword", "standard");
es_index.append("description", "text", "standard", false);
es_index.append("avatar_id", "keyword", "standard", false);
es_index.create();
// 插入文档数据
EsUpdate ud1(client, "user", "_doc", 1);
ud1.addProperty("user_id", "USER4b862aaa-2df8654a-7eb4bb65-11111111");
ud1.addProperty("nickname", "昵称 1");
ud1.addProperty("phone", "手机号 1");
ud1.addProperty("description", "签名 1");
ud1.addProperty("avatar_id", "头像 1");
ud1.submit();
EsUpdate ud2(client, "user", "_doc", 2);
ud2.addProperty("user_id", "USER14eeeaa5-442771b9-0262e455-e4663d1d");
ud2.addProperty("nickname", "昵称 2");
ud2.addProperty("phone", "手机号 2");
ud2.addProperty("description", "签名 2");
ud2.addProperty("avatar_id", "头像 2");
ud2.submit();
}
catch (std::exception &e)
{
std::cout << e.what() << std::endl;
}
return 0;
}
其中,EsIndex
和EsUpdate
对象都以智能指针shared_ptr保存一份es客户端的副本,用于与es服务端交互。
class EsIndex
{
public:
//....
private:
std::shared_ptr<elasticlient::Client> _client;
//...
};
class EsUpdate
{
public:
//....
private:
std::shared_ptr<elasticlient::Client> _client;
//...
};
刚开始以裸指针传入EsIndex
和EsUpdate
,用于其内部创建智能指针。程序运行后报段错误,使用gdb调试后,提示异常信息如下:
不要混用裸指针和智能指针来指向同一块内存。 如果你决定使用智能指针来管理内存,就应完全依赖它,而避免在代码中保留指向同一内存的裸指针。
#include "es.hh"
int main()
{
// 创建es客户端,与es建立连接
try
{
// elasticlient::Client* client = new elasticlient::Client({"http://localhost:9200/"});
auto client = std::make_shared<elasticlient::Client>(std::initializer_list<std::string>{"http://localhost:9200/"});
// 创建索引
EsIndex es_index(client, "user", "_doc");
es_index.append("nickname", "text", "ik_maxword", true);
es_index.append("user_id", "keyword", "standard");
es_index.append("phone", "keyword", "standard");
es_index.append("description", "text", "standard", false);
es_index.append("avatar_id", "keyword", "standard", false);
es_index.create();
// 插入文档数据
EsUpdate ud1(client, "user", "_doc", 1);
ud1.addProperty("user_id", "USER4b862aaa-2df8654a-7eb4bb65-11111111");
ud1.addProperty("nickname", "昵称 1");
ud1.addProperty("phone", "手机号 1");
ud1.addProperty("description", "签名 1");
ud1.addProperty("avatar_id", "头像 1");
ud1.submit();
EsUpdate ud2(client, "user", "_doc", 2);
ud2.addProperty("user_id", "USER14eeeaa5-442771b9-0262e455-e4663d1d");
ud2.addProperty("nickname", "昵称 2");
ud2.addProperty("phone", "手机号 2");
ud2.addProperty("description", "签名 2");
ud2.addProperty("avatar_id", "头像 2");
ud2.submit();
// 搜索内容
// std::string search_body = R"({
// "query": {
// "match_all": {}
// }
// })";
// cpr::Response response = client.search("user", "_doc", search_body);
// std::cout << "状态码: " << response.status_code << std::endl;
// std::cout << "查找内容:" << response.text << std::endl;
}
catch (std::exception &e)
{
std::cout << e.what() << std::endl;
}
return 0;
}