我在指针算术方面遇到了一些麻烦。我认为我理解了概念(指针变量指向内存地址,普通变量指向数据),但我相信我的问题出在语法上(*、&、(*)、*() 等)。
我的目标是构建自定义结构的动态数组(即指向堆结构的指针数组),我的接口提供了两种方法:"ad_to_obj_array"(将要添加的对象和可以为空的数组)和 "obj_array_dustbin"(仅需要处理的数组,同时处理内容,即堆对象)。前者如下所示:
对象的细节并不重要(而且结构已经被重新命名),但是我对一般问题的解决方案如下,如果您能发现错误,我将不胜感激。编译器在我尝试将 RHS 上指针中的地址分配给指向堆结构的指针数组中的指针值时抱怨无效的 lvalue:
#define NUM_ELEM(x) (sizeof (x) / sizeof (*(x)))
obj* add_to_obj_array(obj* new_obj, obj* array)
{
int number_of_elements = 0;
if (array != NULL)
{
number_of_elements = NUM_ELEM(array);
}
obj* new_array = NULL;
/* note: I am expecting sizeof(new_obj) to return the size of an obj*
to go into the array of pointers. */
if ( NULL ==
(new_array = (obj*)malloc((number_of_elements + 1)* sizeof(new_obj))) )
{
/* memory request refused :( */
return NULL;
}
/* copy the old array pointers into the new array's pointer slots: */
int i;
for (i = 0; i < number_of_elements; i++)
{
&(new_array[i]) = &(array[i]);
}
/* add the new item to the end (assign pointer value directly): */
new_array[number_of_elements] = new_obj;
if (number_of_elements > 0)
{
free(&array);
}
return new_array;
}
现在,我已经尝试了以下有问题行的排列方式:
&(new_array[i]) = &(array[i]);
*(new_array[i]) = &(array[i]);
new_array[i] = &(array[i]);
所有这些代码都会产生编译错误。我相当确定右边是旧数组的第i个元素的地址,但是如果数组的元素是指向结构体的指针,那么如何将其赋值给新数组的第i个元素呢?
编辑 - 请注意,上面的NUM_ELEM宏不起作用;它总是返回1。请参见@Merlyn Morgan-Graham下面的答案,了解原因。
void*
是一种“任意指针”类型。指针的大小都相同,你可以将它们强制转换,但最好通过良好的接口记录你的意图,而不是在实现中进行(令人困惑的)强制转换来简化代码。 - Merlyn Morgan-Graham