【问题标题】:What does "#define STR(a) #a" do?“#define STR(a) #a”有什么作用?
【发布时间】:2010-08-20 19:09:07
【问题描述】:

我正在阅读 phoneME 的源代码。这是一个 FOSS JavaME 实现。它是用 C++ 编写的,我偶然发现了这个:

// Makes a string of the argument (which is not macro-expanded)
#define STR(a) #a

我知道 C 和 C++,但我从未读过这样的东西。 #a 中的# 有什么作用?

另外,在同一个文件中,还有:

// Makes a string of the macro expansion of a
#define XSTR(a) STR(a)

我的意思是,定义一个新宏有什么用,如果它所做的只是调用一个现有的宏?

源代码在https://phoneme.dev.java.net/source/browse/phoneme/releases/phoneme_feature-mr2-rel-b23/cldc/src/vm/share/utilities/GlobalDefinitions.hpp?rev=5525&view=markup。您可以使用 CTRL+F 找到它。

【问题讨论】:

标签: c++ c c-preprocessor


【解决方案1】:

在第一个定义中,#a 表示将宏参数打印为字符串。这将转向,例如STR(foo) 转换为 "foo",但不会对其参数进行宏扩展。

第二个定义不会对第一个添加任何内容,但是通过将其参数传递给另一个宏,它会强制对其参数进行完整的宏扩展。所以XSTR(expr) 创建了一个expr 字符串,所有宏都完全展开了。

【讨论】:

    【解决方案2】:

    # 是字符串化操作符。预处理器从参数中生成一个字符串。

    假设你有:

    STR(MyClass);
    

    它将被预处理为:

    "MyClass";
    

    间接级别(使用 XSTR())与宏扩展规则有关。

    【讨论】:

      【解决方案3】:

      首先,您应该知道这对宏实际上是相当常见的。第一个完全按照注释所说的那样 - 它通过将参数括在双引号中来将参数转换为字符串。

      第二个用于引起参数的宏扩展。你通常像这样一起使用它们:

      #define a value_a
      
      printf("%s", XSTR(a));
      

      宏扩展会将a 扩展为string_a,然后stringify 会将其转换为字符串,因此输出将为value_a

      【讨论】:

        【解决方案4】:

        #a 被称为stringizer operator。它接受形式参数,在本例中为 a,并通过将其括在双引号中将其转换为字符串。

        如果你有:

        string s = STR("my quoted string");
        cout << s;
        

        输出将是:

        "my quoted string"
        

        【讨论】:

        • 没关系,但我认为“stringizer”是微软独有的;它通常是“stringify”操作符,这个过程被称为“stringification”
        • 如果你要编词,那么“stringify”和“stringise”就可以互为调侃。我建议“弦”。
        • @John,我相信你的意思是:string s = STR(my quoted string);,即没有引号(和分号)。
        • @John Dibling、@Michael Mrozek:至少在 C++ 中,标准的那部分标题为 [cpp.stringize]
        • @Alok:不,我指的是引号。关键是字符串化器,或者任何你喜欢称之为我个人的东西,我不在乎,将返回一个带引号的字符串。但你对分号是正确的。已添加。
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-12-06
        • 2014-06-01
        • 1970-01-01
        • 2014-02-19
        • 2018-06-27
        • 1970-01-01
        相关资源
        最近更新 更多