Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/loops/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 在循环中初始化预分配的结构实例_C++_Loops_Struct_Instance - Fatal编程技术网

C++ 在循环中初始化预分配的结构实例

C++ 在循环中初始化预分配的结构实例,c++,loops,struct,instance,C++,Loops,Struct,Instance,我想使用malloc()为特定结构的特定数量的实例分配内存。 然后,我想初始化循环中的每个实例。 但是,对于每一次迭代,我观察到构造函数和之后的析构函数都被调用。。。为什么? 更让我惊讶的是,尽管调用了析构函数,我的每个实例都存在于循环之后。。。并且我的实例是用相同的值初始化的! 我肯定错过了一些重要的事情。。。如果有人能帮助我,我将不胜感激,因为目前我无法解释发生了什么。 这是我的C++代码: struct myStruct{ int* a; int* b; myStruct

我想使用malloc()为特定结构的特定数量的实例分配内存。 然后,我想初始化循环中的每个实例。 但是,对于每一次迭代,我观察到构造函数和之后的析构函数都被调用。。。为什么? 更让我惊讶的是,尽管调用了析构函数,我的每个实例都存在于循环之后。。。并且我的实例是用相同的值初始化的! 我肯定错过了一些重要的事情。。。如果有人能帮助我,我将不胜感激,因为目前我无法解释发生了什么。 这是我的C++代码:

struct myStruct{
   int* a;
   int* b;
   myStruct(int x, int y)
   {
    std::cout << "the constructor is called" << std::endl;
    a = (int*)malloc(x*sizeof(int));
    b = (int*)malloc(y*sizeof(float));
   }
   ~myStruct()
   {
       std::cout << "the destructor is called" << std::endl;
       delete[] a;
       delete[] b;
   } };

int main(int argc, char** argv){
int Nb = 3;
myStruct *S = (myStruct*)malloc(Nb*sizeof(myStruct));
for(int i=0 ; i<Nb ; i++)
{
    *(S+i) = myStruct(1,2);
}
std::cout << std::endl;
for(int i=0 ; i<Nb ; i++)
{
    std::cout << "instance " << i << " :" << std::endl;
    std::cout << (unsigned int)(*(S+i)->a) << std::endl;
    std::cout << (unsigned int)(*(S+i)->b) << std::endl << std::endl;
}
system("PAUSE");}
struct myStruct{
int*a;
int*b;
myStruct(整数x,整数y)
{
表达式中的std::cout

*(S+i) = myStruct(1,2)
所发生的情况是,您创建了一个结构的临时实例(
myStruct(1,2)
部分),然后将该实例复制到
S[i]
。复制很浅,因此只复制指针,不分配或复制新数据。表达式完成后,不再需要临时实例,因此它被销毁

这种破坏当然会导致释放数据成员,从而释放数组(副本)中结构中的指针不再有效,访问它们是未定义的行为。此外,您实际上不会将分配的内存初始化为任何内容,因此内存将包含分配之前的内容,并且内容看起来是随机的


我建议您阅读,最重要的是。

每次通过循环,代码都会创建一个临时对象(
myStruct(1,2)
),然后销毁它。这就是输出所显示的内容

该临时对象被分配给未初始化的对象
*(S+i)
,这不是一件好事。对象应该由构造函数而不是赋值运算符初始化。此处使用构造函数的方法是:

new (S+i) myStruct(1,2);
括号中的第一个值是要构造对象的地址


这样做之后,正如其他人所提到的,您不能对结果数组使用
delete
,因为它不是用
new
创建的。因此,您必须循环遍历对象并显式调用每个对象上的析构函数,然后
释放
内存。

您使用
malloc
进行分配,但使用
d进行释放elete
?那不行。谢谢你的回复,Joachim。事实上,我应该使用“new”而不是malloc。这是我的新构造函数:myStruct(int x,int y){std::cout好的,我理解“三个法则”现在!我必须定义一个显式的复制构造函数,以确保当为我的临时实例调用析构函数时,我实例的数据成员将保持安全。@LorentzLorentz复制构造函数和复制赋值运算符。如果您的编译器足够新,还需要它们的版本。谢谢Pete。好的,使用“new”这个位置,析构函数不再被调用,但实例仍使用与我的命令窗口显示的相同值进行初始化:构造函数被调用构造函数被调用构造函数被调用实例0:3452816845 3452816845实例1:3452816845 3452816845实例2:3452816845 3452816845按任意键继续…抱歉皮特,忘了我的最后一个答案。它现在很有效。谢谢你