Как мы можем определить макрос CONCATENATE (x) для расширения только на один слой.... Возможно ли это?
Нет.Вот что у вас есть в наличии.Когда происходит вызов макроса, первым шагом является замена аргумента (как; 6.10.3.1);во время этого шага токены в аргументе оцениваются, если их соответствующий параметр упоминается в списке замены макроса, причем упомянутое упоминание не участвует в строковом преобразовании или вставке.Полученное расширение заменяет указанные параметры в списке замены.Далее стренификация / вставки применяются в произвольном порядке.Наконец, происходит повторное сканирование и дальнейшая замена (rafr; 6.10.3.4p1), во время которой сканируется сам список получаемых замен;во время этого сканирования имя макроса «закрашено синим» (6.10.3.4p2; «синяя краска» не упоминается по имени, но для этого используется технический жаргон ), что означает, что при обнаружении он не будет расширяться дальше.
Итак, давайте посмотрим на это с этой точки зрения.UART_PERIPH
- это идентификатор.Либо он будет распознан как макрос в некотором контексте (то есть вызовет вызов макроса), либо не будет.Не имеет значения, находится ли контекст во время as или rafr;если это вызывается, вызов включает rafr (нет как, потому что он подобен объекту)Таким образом, вызов включает в себя USART2
и повторное сканирование.Единственный возможный способ не расширять USART2
- это чтобы этот идентификатор не был распознан как макрос, но поскольку он в настоящее время определен как единое целое, единственный способ для этого - закрасить этот идентификатор синим цветом.Это невозможно (по крайней мере, в предполагаемом контексте), потому что USART2
должно быть расширено, чтобы это произошло, и к тому времени вы уже вводите токены, которые вам не нужны.