[英]Segmentation fault when Using std::initializer_list<std::string> in Constructor
Hi i am trying to understand how constructors work and so reading different examples.嗨,我正在尝试了解构造函数的工作原理,并阅读不同的示例。 I have a class constructor that takes an initializer_list but it keeps giving
Segmentation fault
.我有一个 class 构造函数,它接受一个 initializer_list 但它不断给出
Segmentation fault
。 The files that i have are as follows:我拥有的文件如下:
class StrVec {
public:
StrVec(): elements(nullptr), first_free(nullptr), cap(nullptr) {
}
StrVec(const StrVec&);
StrVec(std::initializer_list<std::string> il);
StrVec &operator=(const StrVec&);
~StrVec();
void push_back(const std::string&);
void pop_back();
void reserve(std::size_t);
void resize(std::size_t, const std::string& = std::string());
bool empty() const {
return begin() == end();
}
std::size_t size() const {
return first_free - elements;
}
std::size_t capacity() const{
return cap - elements;
}
std::string *begin() const {
return elements;
}
std::string *end() const {
return first_free;
}
private:
static std::allocator<std::string> alloc;
void chk_n_alloc() {
if (size() == capacity()){
reallocate();
}
}
std::pair<std::string*, std::string*> alloc_n_copy(const std::string*, const std::string*);
void free();
void reallocate();
std::string *elements;
std::string *first_free;
std::string *cap;
};
StrVec::StrVec(const StrVec &s){
auto newdata = alloc_n_copy(s.begin(), s.end());
elements = newdata.first;
first_free = cap = newdata.second;
}
StrVec::StrVec(std::initializer_list<std::string> il){
for(const auto &s:il){
push_back(s);
}
}
std::pair<std::string*, std::string*> StrVec::alloc_n_copy(const std::string *b, const std::string *e){
auto data = alloc.allocate(e - b);
return {data, uninitialized_copy(b, e, data)};
}
void StrVec::push_back(const std::string& s){
chk_n_alloc();
alloc.construct(first_free++, s);
}
int main() {
StrVec sv10 { "il1", "il2", "il3", "il4", "il5" };
return 0;
}
My question is how can i resolve this issue and why am i getting this Segmentation fault
and what does it mean so that i can avoid it in the future?我的问题是如何解决这个问题,为什么会出现这个
Segmentation fault
,这意味着什么,以便我将来可以避免它?
PS: I know that the error is due to the StrVec(std::initializer_list<std::string> il);
PS:我知道错误是由于
StrVec(std::initializer_list<std::string> il);
constructor since if i remove this and its use in the mainfile.cpp then Segmentation fault
goes away.构造函数,因为如果我删除它及其在 mainfile.cpp 中的使用,那么
Segmentation fault
就会消失。
[Just guessing here since you don't show a proper minimal reproducible example .] [只是在这里猜测,因为您没有显示适当的最小可重现示例。]
You have a set of pointers in your class.您的 class 中有一组指针。
Your StrVec(std::initializer_list<std::string> il)
constructor does not initialize these pointers, so push_back
will most likely use these uninitialized pointers and you will have undefined behavior and the crash.您的
StrVec(std::initializer_list<std::string> il)
构造函数不会初始化这些指针,因此push_back
很可能会使用这些未初始化的指针,并且您将有未定义的行为和崩溃。
You can easily do the default initialization by delegating it to the default constructor:您可以通过将其委托给默认构造函数轻松地进行默认初始化:
StrVec::StrVec(std::initializer_list<std::string> il)
: StrVec() // Delegte default initialization
{
for(const auto &s:il){
push_back(s);
}
}
With that said, the std::initializer_list
will have a size, which means you can pre-allocate the exact number of elements needed, and then copy them instead of calling push_back
in a loop.话虽如此,
std::initializer_list
将具有大小,这意味着您可以预先分配所需的确切数量的元素,然后复制它们而不是在循环中调用push_back
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.