1. 程式人生 > 其它 >C++中的#與##

C++中的#與##

技術標籤:C++精通之路

內容簡介

#的作用

#用於將一個巨集引數字串化

// 程式碼一
#include <string>
#include <iostream>

#define test_jing(inner_str) #inner_str 

int main()
{
    std::string str="sfjsljfas";
    std::cout<<test_jing(str);
    return 0;
}

可得到輸出:
在這裡插入圖片描述
可見這裡#只是無腦地將巨集引數表示為了字串,相當於直接在巨集引數外邊加了雙引號, 注意比較與str變數所表示的內容的區別。

##的作用

##用於直接拼接其前後的內容,形成一個有意義的C++結構(比如變數名,或者類名等)。

// 程式碼二
#include <string>
#include <iostream>

class Base {
    public: 
        Base(){
            std::cout<<"Base!"<<std::endl;
        }
};

#define test_jing(inner_str1, inner_str2) inner_str1##inner_str2
int main
() { std::string str1="Ba"; std::string str2="se"; test_jing(Ba, se) a; return 0; }

在這個例子裡面test_jing(Ba, se)的拼接結果是Base是一個基類名,因而test_jing(Ba, se) a;就是一個構造Base類的a物件的過程,其輸出如下:
在這裡插入圖片描述

注意點

凡是巨集定義裡有用#或##的地方巨集引數是不會再展開

如果想要使其中的巨集引數展開,則需要多加一層中間轉換巨集

加這層巨集的用意是把所有巨集的引數在這層裡全部展開,那麼在轉換巨集裡的巨集就能得到對應的巨集引數。

//示例三
#include <string>
#include <iostream>

#define test_jing(inner_str1, inner_str2) inner_str1##inner_str2
#define macro_str_print(str) #str
#define macro_str_print1(inner_str1, inner_str2) macro_str_print(test_jing(inner_str1, inner_str2))
int main()
{
    std::cout<<macro_str_print1(str1, str2);
    return 0;
}

在示例三中,想要把str1和str2拼接成str1str2並以字串輸出,但是在展開macro_str_print(str1, str2)之後,得到的是macro_str_print(test_jing(str1, str2))。進一步展開,得到,#test_jing(str1, str2)。由於#和##都不會再對巨集引數進行展開,因此得到的輸出是:
在這裡插入圖片描述
並非我們所希望的。

//示例四
#include <string>
#include <iostream>

#define test_jing(inner_str1, inner_str2) inner_str1##inner_str2
#define test_jing_help(inner_str1, inner_str2) test_jing(inner_str1, inner_str2) /*間接層1*/
#define macro_str_print(str) #str
#define macro_str_print_help(str) macro_str_print(str) /*間接層2*/
#define concatenate_print(inner_str1, inner_str2) macro_str_print_help(test_jing_help(inner_str1, inner_str2)) /*這裡也可以選擇不要間接層1,直接寫test_jing,也可以得到正確的展開結果(只需要保證在遇到#或者##之前,所有的巨集都已經展開即可)*/
int main()
{
    std::cout<<concatenate_print(str1, str2);
    return 0;
}

在示例四中,通過引入了兩個間接層得到了正確的輸出,示例四的輸出在這裡插入圖片描述
具體的原因是與展開順序有關的,可以參考c語言中的巨集展開