2016-05-13 81 views
0

我已经在已有的结构St中引入了一个新的矢量St,就像这样std::vector<X> xInfo; X是另一个新定义的结构,它包含原始数据类型的成员。现在有一个预先存在的代码,如memset(&s, 0, sizeof(St));,其中s是St.的一个实例。由于在St中添加了向量xInfo,会导致什么类型的问题?结构中的矢量初始化

如何克服这些问题,以便我可以在结构中保留新的矢量?

编辑:下面是对形势

// Below section is new code. 

typedef struct 
{ 
    char m11; 
    int  m12; 
    char m13[50]; 
}X; 
// Below section is existing code. 

typedef struct{ 
    char    m1[10]; 
    int    m2; 
    long    m3; 
    double   m4; 
vector<X>  xInfo; /* this line is newly added code */ 
}St; 

void fun(const char* a1, int a2, long m3, double m4) 
{ 
    St s; 

    memset(&s, 0, sizeof(St)); 

    if(NULL != a1 && 0 != a1[0]) 
     strncpy(m1, a1, 9); 

    m2 = a2; 
    m3 = a3; 
    m4 = a4; 

    ........ 
    ........ 
} 
+1

对于类对象使用memset()并不是一个好主意,特别是像std :: vector(你不知道它是如何构建的)的STL项目。如果您提供代码,我们可能会提供更多有用的反馈。我认为memset()可以用于任何POD项目,但通常情况下,分配更容易。请查看[MCVE]。 –

+4

*现在有一个预先存在的代码,如memset(&s,0,sizeof(St))* - 好了,说白了,是时候改变'memset'代码了,否则你会在很多悲伤中。 – PaulMcKenzie

+0

@ DOUGLASO.MOEN我在编辑部分添加了代码示例,请提供解决方案以保留新代码的现有行为。除了添加'St'的构造函数外,还有其他解决方案吗? –

回答

2

这将导致未定义行为的示例代码。

翻译:最有可能是一个崩溃。

1

memset()肯定会混淆你的运行时间。

St s; 
memset(&s, 0, sizeof(St)); 

因为s包含一个std :: vector的,您的载体将被这个memset的踩踏(),而不是你想要的方式。

正如我在上面的评论中所说的,你做而不是知道如何构建std :: vector <>。例如,在Ubuntu 15.10上,使用g ++ 5.2.1,一个std :: vector <>只有24个字节,而不管有多少个元素。下面是从我的一个小程序的部分输出:

typedef std::vector<UI224> VecUI224; 
sizeof(VecUI224)    : 24 

VecUI224 vui224; 
sizeof(vui224) : 24 vui224.size() = 000000 vui224.capacity() : 00000 
sizeof(vui224) : 24 vui224.size() = 000001 vui224.capacity() : 00001 
sizeof(vui224) : 24 vui224.size() = 100  vui224.capacity() : 128 
sizeof(vui224) : 24 vui224.size() = 200  vui224.capacity() : 256 
// ... 
sizeof(vui224) : 24 vui224.size() = 900  vui224.capacity() : 1024 
sizeof(vui224) : 24 vui224.size() = 1000  vui224.capacity() : 1024 

IMHO(I尚未检查的矢量模板代码)的24个字节包含一些指针和开销。推断的指针指向堆,并且没有数据将存在于矢量对象中。使用memset()跺脚只会破坏向量,X的数据不存在

您现有的memset()只会清除这些向量指针和开销,而不是数据。可能导致崩溃。

初始化结构(或类)的正确方法是创建一个构造函数,并通过适当的初始值设定项列表赋值。

例1是C风格,并且你确实需要移动到C++:

typedef struct{ 
    char    m1[10]; 
    int    m2; 
    long    m3; 
    double   m4; 
    vector<X>  xInfo; /* this line is newly added code */ 
}St; 

一个可能的C++方法:创建构造函数,添加一个初始化列表。

struct St_t // I use suffix '_t' to indicate a type 
{ 
    St_t (void) : // ctor 
     // m1[10] see body of ctor 
     m2 (0), 
     m3 (0), 
     m4 (0) 
     // xInfo - see default ctor of X_t below 
    { 
     // it is ok to consider this, but raises the wtf factor 
     ::memset(m1, 0, 10); // for the single pod 
    } 
    char    m1[10]; 
    int    m2; 
    long    m3; 
    double   m4; 

    vector<X_t>  xInfo; /* this line is newly added code */ 
}; 

的为信佛,C++的方法可能是类似以下内容:男星在

struct X_t 
{ 
    X_t(void) : // type X_t default dtor 
     m11(0), 
     m12(0) 
     // m13 
    { 
     // I would fill m13 with 
     for (int i=0;i<50; ++i) 
     m13[i] = 0; 
    } 
    char m11; 
    int  m12; 
    char m13[50]; 
}; 

初始化所有数据字段(这里为0)。每当你实例化另一个实例时,这些ctor确保数据被初始化。


...还有没有其他的解决办法...?

软件是非常灵活的,但ctor是最简单和最自我记录的方法。


如何克服这些问题,这样我可以保持新的向量内 结构?

我看到没有问题保持旧结构中的矢量。 Ctor是最合适的方法。

+0

谢谢@DOUGLAS,我用相同的方法实施。 –