class MyString
{
public:
MyString(int length):_ptr(alloca(length))
{
}
//Copy Constructor, destructor, other member functions.
private:
void* _ptr;
};
int main()
{
MyString str(44);
return 0;
}
是在main函数结束时释放,还是在构造函数执行后立即释放?这是一个好主意,有一个像这样的字符串类,如果上面的代码工作如预期?
更新:
看起来主要的危险是
- StackOverflow
- 构造函数内联
我想我可以通过使用alloca小尺寸和malloc/free大尺寸来照顾StackOverflow。我猜一定有一些非可移植编译器特定的方式来强制编译器内联。
我很感兴趣,因为字符串类在任何c++项目中都被广泛使用。如果我做对了,我期待着一个巨大的性能提升,因为大多数分配都在堆栈内,否则会进入堆。这将是一个实用程序,最终用户将不知道内部。
根据alloca的文档,当alloca的调用者返回时释放内存。因此,如果编译器将初始化列表视为构造函数的一部分,则在构造函数结束时释放内存,即在执行初始化列表之前创建堆栈帧。如果堆栈帧是在初始化列表执行之后创建的,那么分配的内存将在构造函数的调用者中,因此,在这种情况下,内存在main结束时被释放。我不太了解这个标准,不能绝对确定它会以哪种方式发生。
但是,无论何时释放内存,ptr
的值都不会改变。
显然,类成员的初始化是作为c'tor的一部分执行的。因此,至少按照标准,alloca
返回的指针的有效性被限制为c'tor。
所以像你这样初始化你的类成员似乎是一个非常糟糕的主意。
OTOH以下将没有问题:
class MyString
{
public:
MyString(void* ptr):_ptr(ptr)
{
}
//Copy Constructor, destructor, other member functions.
private:
void* _ptr;
};
int main()
{
MyString str(alloca(44));
return 0;
}