我可以在C中执行类似#define ARRAY(size)char [## size ##]的操作吗?

yli*_*ima 4 c gcc avr avr-gcc

我正在尝试定义一个宏来在我的全局范围内生成一个结构,如上面的代码:

#define BUFFER(size) \
struct { \
    unsigned short size = ##size; \
    unsigned short readIndex = 0; \
    unsigned short writeIndex = 0; \
    unsigned char dataPtr[##size##]; \
}

BUFFER(10) buffer10bytes;
BUFFER(50) buffer50bytes;
Run Code Online (Sandbox Code Playgroud)

问题是显然gcc没有评估这个宏.存档是否可能?怎么样?

这是我的编译器错误:

In file included from ../usart.c:12:0:
../usart.c:14:8: error: expected identifier or '(' before numeric constant
 BUFFER(10) buffer10bytes;
        ^
../buff.h:24:17: note: in definition of macro 'BUFFER'
  unsigned short size = ##size; \
                 ^
../buff.h:24:22: error: pasting "=" and "10" does not give a valid preprocessing token
  unsigned short size = ##size; \
                      ^
../usart.c:14:1: note: in expansion of macro 'BUFFER'
 BUFFER(10) buffer10bytes;
 ^
../buff.h:25:27: error: expected ':', ',', ';', '}' or '__attribute__' before '=' token
  unsigned short readIndex = 0; \
                           ^
../usart.c:14:1: note: in expansion of macro 'BUFFER'
 BUFFER(10) buffer10bytes;
 ^
../buff.h:27:23: error: pasting "[" and "10" does not give a valid preprocessing token
  unsigned char dataPtr[##size##]; \
                       ^
../usart.c:14:1: note: in expansion of macro 'BUFFER'
 BUFFER(10) buffer10bytes;
 ^
../usart.c:14:8: error: pasting "10" and "]" does not give a valid preprocessing token
 BUFFER(10) buffer10bytes;
        ^
../buff.h:27:26: note: in definition of macro 'BUFFER'
  unsigned char dataPtr[##size##]; \
                          ^
../usart.c:15:8: error: expected identifier or '(' before numeric constant
 BUFFER(50) buffer50bytes;
        ^
../buff.h:24:17: note: in definition of macro 'BUFFER'
  unsigned short size = ##size; \
                 ^
../buff.h:24:22: error: pasting "=" and "50" does not give a valid preprocessing token
  unsigned short size = ##size; \
                      ^
../usart.c:15:1: note: in expansion of macro 'BUFFER'
 BUFFER(50) buffer50bytes;
 ^
../buff.h:25:27: error: expected ':', ',', ';', '}' or '__attribute__' before '=' token
  unsigned short readIndex = 0; \
                           ^
../usart.c:15:1: note: in expansion of macro 'BUFFER'
 BUFFER(50) buffer50bytes;
 ^
../buff.h:27:23: error: pasting "[" and "50" does not give a valid preprocessing token
  unsigned char dataPtr[##size##]; \
                       ^
../usart.c:15:1: note: in expansion of macro 'BUFFER'
 BUFFER(50) buffer50bytes;
 ^
../usart.c:15:8: error: pasting "50" and "]" does not give a valid preprocessing token
 BUFFER(50) buffer50bytes;
        ^
../buff.h:27:26: note: in definition of macro 'BUFFER'
  unsigned char dataPtr[##size##]; \
                          ^
make: ** [usart.o] Erro 1
Run Code Online (Sandbox Code Playgroud)

M.M*_*M.M 8

取出来##.这是用于从两个令牌创建新令牌; 但你不是在这里做,你实际上只想要两个令牌.

此外,您不能使用与宏参数相同的变量名称.

另一个问题是你不能在结构定义中放置初始化器.所以你必须修改宏的形式,例如:

#define DECLARE_BUFFER(size_, name) \
struct { \
    unsigned short readIndex;
    unsigned short writeIndex;
    unsigned char dataPtr[size_]; \
} name = { 0 }

BUFFER(10, buffer10bytes);
BUFFER(50, buffer50bytes);
Run Code Online (Sandbox Code Playgroud)

我已经删除,size因为它似乎是多余的:你总是可以sizeof X.dataPtr去获得这个价值.(注意:Ptr数组的名称很差).但是size如果需要(如Remy在评论中所建议的那样),如果要更改为表示缓冲区的内容或其他内容,则可以包括:

#define DECLARE_BUFFER(size_, name) \
struct { \
    unsigned short size;
    unsigned short readIndex;
    unsigned short writeIndex;
    unsigned char dataPtr[size_]; \
} name = { size_, 0 }
Run Code Online (Sandbox Code Playgroud)

  • 此外,您不能在C结构定义中进行成员初始化. (2认同)