为什么在Gnu gcc/g++;? 考虑这个无害的C++程序: #include <iostream> int main() { std::cout << "(Is this a trigraph??)" << std::endl; return 0; }
为什么要为三角图解析字符串文字为什么在Gnu gcc/g++;? 考虑这个无害的C++程序: #include <iostream> int main() { std::cout << "(Is this a trigraph??)" << std::endl; return 0; },c++,gcc,trigraphs,C++,Gcc,Trigraphs,为什么要为三角图解析字符串文字 其他编译器也这样做吗?三角图是在翻译阶段1中处理的(然而,它们在C++17中被删除)。与字符串文字相关的处理在后续阶段进行。正如C++14标准所规定的(n4140): 翻译语法规则的优先顺序由 以下阶段 物理源文件字符以实现定义的方式映射到基本源字符集 (为行尾指示器引入新行字符)如果 必需的已接受物理源文件字符集 实现定义Trigraph序列([lex.Trigraph])是 替换为相应的单字符内部表示。 不在基本源字符集中的任何源文件字符 ([lex.char
其他编译器也这样做吗?三角图是在翻译阶段1中处理的(然而,它们在C++17中被删除)。与字符串文字相关的处理在后续阶段进行。正如C++14标准所规定的(n4140): 翻译语法规则的优先顺序由 以下阶段
这是首先发生的,因为正如在注释中告诉您的那样,trigraphs所代表的字符也需要可打印。trigraphs是在翻译阶段1中处理的(但是在C++17中它们被删除)。与字符串文字相关的处理在后续阶段进行。正如C++14标准所规定的(n4140): 翻译语法规则的优先顺序由 以下阶段
这种情况首先发生,因为正如在评论中告诉您的那样,trigraphs所代表的字符也需要可打印。这种行为继承自C编译器和旧时代,当时我们使用的串行终端只使用了7位(第8位是奇偶校验位)。为了允许使用特殊字符的非英语语言(例如,法语中的重音字母或西班牙语中的字母),代码页使用一些ASCII(7位)代码来表示它们。特别是,代码0x23、0x24(
$
)0x40(@
)、0x5B到0x5E([\]^
)、0x60(`)和0x7B到0x7E({124;}
)可以用国家变量替换1
因为它们在C语言中有特殊的含义,所以它们可以在源代码中替换为仅使用ISO 646不变部分的三角图
出于兼容性的原因,这一直保持到C++14,当时只有恐龙还记得ISO646和仅7位代码页的时代(不太好)
1例如,使用的法语变体:0x23
、0x40a
0x5B-0x5D§
、0x60µ
、0x7B-0x7E
这一行为继承自C编译器和以前使用串行终端时仅使用了7位(第8位为奇偶校验位)。为了允许使用特殊字符的非英语语言(例如,法语中的重音字母或西班牙语中的字母),代码页使用一些ASCII(7位)代码来表示它们。特别是,代码0x23、0x24($
)0x40(@
)、0x5B到0x5E([\]^
)、0x60(`)和0x7B到0x7E({124;}
)可以用国家变量替换1
因为它们在C语言中有特殊的含义,所以它们可以在源代码中替换为仅使用ISO 646不变部分的三角图
出于兼容性的原因,这一直保持到C++14,当时只有恐龙还记得ISO646和仅7位代码页的时代(不太好)
1例如,所使用的法语变体:0x23、0x40a
0x5B-0x5Dç§
、0x60µ
、0x7B-0x7E三角图被发明为能够键入在所有系统上可能不可用的特殊字符。当然,它们也可能需要打印。我相信它们在C++17时就已经被弃用了,但在此之前,任何符合标准的编译器都应该扫描它们。我不清楚你到底在问什么。您认为字符串文字应该免于trigraph处理,这有什么原因吗?trigraph的发明是为了能够键入在所有系统上都不可用的特殊字符。当然,它们也可能需要打印。我相信它们在C++17时就已经被弃用了,但在此之前,任何符合标准的编译器都应该扫描它们。我不清楚你到底在问什么。您认为字符串文字应该免于trigraph处理,这有什么原因吗?回答得很好,谢谢!我从来没有想到三角图的印刷适性,一个
me@my-laptop:~/code/C++$ g++ -c test_trigraph.cpp
test_trigraph.cpp:4:36: warning: trigraph ??) ignored, use -trigraphs to enable [-Wtrigraphs]
std::cout << "(Is this a trigraph??)" << std::endl;
^
(Is this a trigraph??)