C编程-结构体赋值

Posted by 周思进 on March 22, 2020

有时候写测试代码,需要对结构体变量进行赋值,能够快速方便的对结构体成员变量进行赋值操作,修改测试也会比较方便,下面对于结构体的几种赋值方式进行说明。

使用的测试结构体声明如下

typedef struct student_t {
    int age;
    char name[32];
    char addr[64];
}STUDENT;


方式一

    STUDENT zhou = {0};
    zhou.age = 30;
    strncpy(zhou.name,  "zhousijin", sizeof(zhou.name));
    strncpy(zhou.addr,  "hangzhou", sizeof(zhou.addr));

对结构体的成员变量依次进行赋值,应该是最常用的方式。


方式二

    STUDENT zhou = {30, "zhousijin", "hangzhou"};

在声明变量的时候直接进行赋值操作,相比方式一省去了不少赋值代码操作,不过这种方式因为变量和值之间的对应关系不直观体现,对于结构体有很多个成员变量的情况下,就非常不友好了,很有可能就漏赋值,或赋值错了对象。


方式三

    STUDENT zhou = {
        .age = 30,
		.addr = "hangzhou",
        .name = "zhousijin"
    };

该方式同样是在声明变量的时候就进行赋值初始化,相比方式二则是变量和值之间的对应关系有了直观的体现,不会搞错赋值,变量赋值顺序上也没有要求。


方式四

两个同类型的结构体之间可以直接通过等号进行赋值,比如已经有赋值好的STUDENT zhou,需要拷贝给STUDENT ying,那么可以直接进行如下赋值

	ying = zhou;

这种场景一般就是一个get操作接口,不过需要明确的是其结构体成员变量中没有存在指针这类申请内存空间后进行赋值的,否则上面只是浅拷贝,后面如果zhou指针内容发生变更,ying指针中的内容也同样发生变更了。

还需要注意的是,有时候外部入参结构体可能不是直接使用的内部结构体的同一个声明类型,只是暂时内部成员变量是一致的,当后面其中一方内部结构体成员变量发生更改,直接赋值这样的方式极大可能就会出现问题,而如果是一个一个的成员变量进行拷贝赋值的,则还可能不会有问题。

再需要注意的是,这种等号赋值操作不能用在数组变量上面~


有些结构体成员变量本身又是一个结构体或联合体之类的,那么赋值访问的时候取值路径会相对较长,可以使用#define来进行一些简化操作,比如像ipv6这样的处理方式

/*
 * IPv6 address
 */
typedef struct in6_addr {
	union {
		__uint8_t   __u6_addr8[16];
		__uint16_t  __u6_addr16[8];
		__uint32_t  __u6_addr32[4];
	} __u6_addr;                    /* 128-bit IP6 address */
} in6_addr_t;

#define s6_addr   __u6_addr.__u6_addr8

那么对于struct in6_addr这样的变量进行赋值操作,可以方便的使用s6_addr来操作。