使用静态const结构限制C中常量的名称冲突有什么问题吗?

Mat*_*att 7 c struct const constants name-collision

例如,如果我要static const struct在header(.h)文件中创建这样的层次结构:

static const struct {
    struct {
        char STATIC /* = 0 */;
        char DYNAMIC /* = 1 */;
    } ALLOCATION;
    struct {
        char TABLE /* = 0 */;
        char LIST /* = 1 */;
        char TREE /* = 2 */;
    } STRUCTURE;
} FOO_STRATEGY = { {0, 1}, {0, 1, 2} };

foo_t *foo_create(char allocation_strategy, char structure_type);
Run Code Online (Sandbox Code Playgroud)

然后将使用这样的东西:

foo_t *foo = foo_create(FOO_STRATEGY.ALLOCATION.STATIC, FOO_STRATEGY.STRUCTURE.TREE);
Run Code Online (Sandbox Code Playgroud)

我想我有一个由两部分组成的问题:

  1. 这是否像人们期望的那样有效?
  2. 为什么其他人不这样做?

Bri*_*and 3

我看到四个可能的问题。如果你不关心这些,那就去吧。

  1. 您将失去执行此示例之类的操作的能力,其中枚举值用于“命名”数组中的索引,并且枚举中的最后一个条目自动给出数组大小。

    typedef enum {
       COLOR_RED,
       COLOR_GREEN,
       COLOR_BLUE,
       NUM_COLORS  
    } Color;
    
    
    int myPallete[NUM_COLORS];
    myPallete[COLOR_RED] = 0xf80000;
    
    Run Code Online (Sandbox Code Playgroud)

    可能还有其他方法可以使用#defineorenum作为常量,但您的方法在 C 中不起作用。这只是我首先想到的。

  2. 以这种方式在标头中声明结构会将该结构的副本放入生成的每个目标文件中。浪费的内存使得这对深度嵌入式系统不友好,因为每个目标文件浪费 5 个字节或 RAM 会很糟糕。将结构放入一个“.c”文件中并使用 extern 在标头中声明它可能会有所帮助。

  3. 没有其他人这样做,所以你创建的代码会让其他人第一次查看你的代码时出错,尽管我认为调整起来并不难。我不在乎你的意见在这里。如果多个评论员说这会令人困惑,那么你已经让那些人感到困惑了。

  4. 这对于防止名称冲突几乎没有作用(也许没有作用?)。标头是否实例化该结构体或实例化该结构体都没有区别#define FOO_STRATEGY。如果您在 enum/#define 值上使用良好的前缀,则包含该标头的任何内容都有相同的名称冲突可能性。

  • @Matt,RE #2,你一般来说可能是对的。但不幸的是,深度嵌入式世界中的许多编译器(想想 0.10 美元、带有 2kB RAM 的 8 位 MCU)远非理智。例如,我很好奇 microchip 的 PIC 编译器会做什么。 (3认同)