1

使用以下(简化的)数据定义:

#define DIM0 10
#define DIM1 15

typedef struct {
    uint32_t var1:
    ...
    int8_t arrayVar1[DIM0];
 } dataClass0;

typedef struct {
    uint32_t var1:
    ...
    int8_t arrayVar1[DIM1];
 } dataClass1;

在一个给定的点上,我必须创建这些结构的数组并处理它们。

除了数组(不同长度)之外,处理完全相同。现在它是这样的:

 dataClass0 *data;
 data = (dataClass0 *) malloc(dimension * sizeof (dataClass0));
 // Processing and filling structure
 data[i].var1 = <value>
 ...

现在我为每个数据类复制了相同的函数。使用这些数据结构时有没有办法避免重复代码?

笔记:

  • 只有纯 C,没有 C++;
  • 我无法更改数据定义(即不能int8_t *arrayVar1在结构中使用)。
  • 处理时,我收到要处理的数据类型(0 表示 class0,1 表示 class1,...)。
4

3 回答 3

3
typedef struct {
    uint32_t var1:
    ...
    int8_t arrayVar[];    /* Declare as flexible array, allowed since C99 */
} dataClass;

分配类似的东西:

data1 = malloc(sizeof (dataCLass) + DIM1*sizeof ((dataClass*)NULL)->arrayVar[0]);
data2 = malloc(sizeof (dataCLass) + DIM2*sizeof ((dataClass*)NULL)->arrayVar[0]);
or define
#define ALLOCDATA(dim) malloc(sizeof (dataCLass) + (dim)*sizeof ((dataClass*)NULL)->arrayVar[0]);

定义

#define ELEMENT1(data, i) (dataClass*)(((char*)(data))+(i)*(DIM1+sizeof (dataCLass)))
#define ELEMENT2(data, i) (dataClass*)(((char*)(data))+(i)*(DIM2+sizeof (dataCLass)))

或者如果您将 DIM 参数化

#define ELEMENT(data, i, dim) (dataClass*)(((char*)(data))+(i)*((dim)+sizeof (dataCLass)))

请享用

ELEMENT1(data1, i)->var1 = 1;
ELEMENT1(data1, i)->arrayVar1[9] = 4;


ELEMENT2(data2, i)->arrayVar1[14] = 4;

或者

ELEMENT(data1, i, DIM1)->var1 = 1;
ELEMENT(data1, i, DIM1)->arrayVar1[9] = 4;


ELEMENT(data2, i, DIM2)->arrayVar1[14] = 4;

不完美,但不是太奇怪的构造不可用。

编辑: ELEMENT 定义应更改为

#define ELEMENT1(data, i) (dataClass*)(((char*)(data))+(i)*(DIM1*sizeof ((dataClass*)NULL)->arrayVar[0]+sizeof (dataCLass)))
#define ELEMENT2(data, i) (dataClass*)(((char*)(data))+(i)*(DIM2*sizeof ((dataClass*)NULL)->arrayVar[0]+sizeof (dataCLass)))

#define ELEMENT(data, i, dim) (dataClass*)(((char*)(data))+(i)*((dim)*sizeof ((dataClass*)NULL)->arrayVar[0]+sizeof (dataCLass)))

通过此更改,您的 arrayVar 字段可以是任何类型,并且不限于大小为 1 的元素。

于 2013-03-27T12:42:07.230 回答
1

你不能让数组动态吗?所以你创建你的结构,malloc()然后初始化一些成员来保存大小(并确保它以一个uint8_t *而不是一个实际的数组结尾,或者使用 VLA)?

于 2013-03-27T12:27:02.453 回答
0

这取决于您是否要最初用不同的值填充数组。否则,您可以只使用一个宏来初始化两种类型的结构

#define STRUCTURE_INITIALIZER(VAR1, VAR2) { .var1 = (VAR1), .var2 = (VAR2) }

并将其用作

dataClass0 data = STRUCTURE_INITIALIZER(31, 42);

0然后,无论它们的大小如何,您的数组组件都将始终被初始化。

要初始化malloc你的东西的 ed 数组:

dataClass0 *data  = malloc(dimension * sizeof (dataClass0));

// Processing and filling structure
for (size_t i = 0; i < dimension; ++i)
  data[i]= (dataClass0)STRUCTURE_INITIALIZER(43, i);

顺便说一句,更喜欢正确初始化变量并且不要强制返回malloc.

于 2013-03-27T13:00:44.560 回答