代码之家  ›  专栏  ›  技术社区  ›  0andriy

为什么填充结构的helper宏需要显式转换?[副本]

  •  0
  • 0andriy  · 技术社区  · 7 年前

    考虑一下声明:

    struct my_cool_struc {
       int field_x;
       int field_Y;
       int field_z;
    };
    
    #define MY_COOL_MACRO(x,y,z) \
      { \
        .field_x = (x), \
        .field_y = (y), \
        .field_z = (z), \
      }
    
    static const struct my_cool_struc why[] = {
      MY_COOL_MACRO(1,2,3),
      MY_COOL_MACRO(6,5,4),
      MY_COOL_MACRO(7,8,9),
      {}
    };
    
    static int my_cool_func(...)
    {
       struct my_cool_struc p[10];
       int a1, a2, a3;
       unsigned int index = 0;
    ...
       p[index++] = MY_COOL_MACRO(a1, a2, a3);
    ...
       return 0;
    }
    

    why 赋值一切正常,编译器无法构建函数,语法分析器失败。

    以下内容修复了此问题:

    - { \
    + (struct my_cool_struc) { \
    

    - p[index++] = MY_COOL_MACRO(a1, a2, a3);
    + p[index++] = (struct my_cool_struc)MY_COOL_MACRO(a1, a2, a3);
    

    编译器是Linux上的GCC(不同版本)。

    1 回复  |  直到 7 年前
        1
  •  3
  •   Lundin    7 年前

    MY_COOL_MACRO 在声明中使用时,正在使用 指定的初始化者 ,这是仅在初始化期间存在的功能。分配期间不能使用它们。

    原因是 (struct my_cool_struc)MY_COOL_MACRO 解决分配期间的问题,因为它根本不是强制转换。而是创建一个临时的、未命名的对象,称为 复合文字 :

    (struct my_cool_struc){ .field_x = (x), .field_y = (y), .field_z = (z) }
    

    由于您正在创建一个对象 { } 是一个初始值设定项列表,您可以在其中使用指定的初始值设定项。

    然后在运行时将复合文字分配给数组项,这很好。