通过引用传递结构并对其进行操作

时间:2009-11-28 05:41:09

标签: c data-structures pointers argument-passing strdup

typedef struct unit_class_struct {
    char *name;
    char *last_name;
} person;


int setName(person *array) {

    array[0].name = strdup("Bob");
    array[1].name = strdup("Dick");

    return 1;
}

int setLastName(person *array) {

    array->last_name = strdup("Sanchez");
    array++;
    array->last_name = strdup("Clark");

    return 1;
}

int main()
{
    person array[10];
    person *pointer;
    pointer = array;
    setName(pointer);
    setLastName(pointer);
    printf("First name is %s %s\n", array[0].name, array[0].last_name);
    printf("Second name is %s %s\n", array[1].name, array[1].last_name);
    while(1) {}
    return 0;
}

这是我提出的用于解决结构问题的一些示例代码。 请注意我在setName中设置名称的方式以及我在setLastName中的设置方式。

两者都有效,但我很好奇我这两种方式之间的区别是什么?

一种方式比另一方好吗?

在这个例子中还需要strdup吗?如果没有,是否有必要将array.name设置为随机大小的变量而不是字符串文字?

4 个答案:

答案 0 :(得分:1)

如果将所有.name设置为字符串常量,则不需要strdup。如果你稍后要修改字符串,你会想要它。指针和内存管理的更好基础将使区分清晰。如果您使用strdup,请务必稍后free结果。

答案 1 :(得分:1)

这两个选项都非常危险,因为你不知道数组的长度。因此,访问array ++或array [1]的结果可能会导致未定义的行为。

也许你可以试试这个apprach

int set_last_name(person* array, char* lastnames[],size_t amount){
    int i=0;

    for(;i<amount;i++,array++){
      strncpy(array->lastname,lastnames[i],strlen(lastnames[i]));
    }

     return 1;
 }

其中amount是lastnames数组的长度。

请注意,没有使用strdup。此函数希望用户为lastnames和array分配内存。然后,如果需要,用户应释放该内存。 我不喜欢strdup,因为它返回一个堆分配的字符串,在你的函数的情况下,应该清楚地记录函数的用户必须释放它。

答案 2 :(得分:0)

在我看来,使用索引方法比使用指针算法更清晰,但两者都有效。我怀疑编译器为每个代码生成的代码在两个实例中非常相似。

如果你正在使用变量,那么

strdup是必要的,因为你没有分配内存来保存person结构中的字符串值。如果您在调用任何一个setter时已经为这些字符串分配了空间,那么strcpystrcpy_s,最好)就足够了。

在您的示例中使用文字时,strdup不是必需的:您可以直接指定char*

答案 3 :(得分:0)

array->name(*array).name完全相同。

在两个函数中,“array”是指向结构的指针,因此*arrayarray[0]都是结构,您可以设置它们的成员。箭头符号只是一种常用的快捷方式。