在同一结构中使用struct成员作为数组大小

时间:2014-02-15 23:16:13

标签: c arrays struct

我是结构化c编码的新手。我不知道我是否可以按如下方式定义结构:

typedef struct command_struct {
    uint8_t com_byte_num;
    uint8_t command_bytes[com_byte_num];
    } command;

并在另一个结构中使用它:

typedef struct commands_struct {
    command poll_dig;
    command poll_joy;
    command poll_all;
    command enter_config;
    command exit_config;
    command conf_set_analog;
    command conf_set_digital;
    command conf_vib_off;
    command conf_joy_only;
    command conf_joy_press;
} commands;

uint8_t command_bytes[com_byte_num];部分是我不确定的。

2 个答案:

答案 0 :(得分:1)

你不能在标准C中执行uint8_t command_bytes[com_byte_num]; - 数组大小必须是固定的(常量),或者你需要符号uint8_t command_bytes[];,它被称为“灵活的数组成员”。 / p>

(但是,请参阅另一个关于VLAIS的答案 - 结构中的可变长度数组。但请注意,此类数组只能由GCC编译,并且它们只能在函数内定义,这极大地复杂化将指针传递给其他函数的过程。)

如果使用灵活的阵列成员,则无法创建第二个结构。如果它包含指向command元素的指针,则可以执行此操作,但如果它包含实际的struct command元素则不能执行此操作。将发生以下两件事之一:

  1. 编译器抱怨你不能这样做。
  2. 编译器允许您这样做,但所有command元素都有一个零大小的command_bytes成员。
  3. 对你没有任何帮助。鉴于代码:

    #include <stdint.h>
    
    typedef struct command_struct
    {
        uint8_t com_byte_num;
        uint8_t command_bytes[];
    } command;
    
    typedef struct commands_struct
    {
        command poll_dig;
        command poll_joy;
        command poll_all;
        command enter_config;
        command exit_config;
        command conf_set_analog;
        command conf_set_digital;
        command conf_vib_off;
        command conf_joy_only;
        command conf_joy_press;
    } commands;
    

    命令:

    $ gcc -O3 -g -std=c11 -Wall -Wextra -Werror -c fla.c
    

    编译文件OK(在Mac OS X 10.9.1 Mavericks上使用GCC 4.8.2)。如果您添加-pedantic,那么您会得到一系列错误,例如:

    fla.c:11:13: error: invalid use of structure with flexible array member [-Werror=pedantic]
         command poll_dig;
    

    如果您更改如下所示的代码,即使是迂腐的编辑也很高兴:

    #include <stdint.h>
    
    typedef struct command_struct
    {
        uint8_t com_byte_num;
        uint8_t command_bytes[];
    } command;
    
    typedef struct commands_struct
    {
        command *poll_dig;
        command *poll_joy;
        command *poll_all;
        command *enter_config;
        command *exit_config;
        command *conf_set_analog;
        command *conf_set_digital;
        command *conf_vib_off;
        command *conf_joy_only;
        command *conf_joy_press;
    } commands;
    

答案 1 :(得分:0)

在gcc中允许使用VLAIS(结构中的可变长度数组)(我认为是最新的C标准),但变量数组必须始终是结构的最后一个成员(因此编译器知道所有成员的位置) ...)。在某种程度上,这意味着:1。只能有一个! (变量长度数组,即...)
2.如果结构是另一个结构的成员,它又必须是该结构的最后一个成员。