考虑表达式*(1+"AB" "CD"+1)
这个表达的解决方案是什么?上面的表达式是C中的开关表达式。
*(2+"AB" "CD") --> *(2+"ABCD") --> ?
在此之后该怎么办? 以下是代码段:
#include<stdio.h>
void main(){
switch(*(1+"AB" "CD"+1)){
case 'A':printf("Pulp Fiction");
break;
case 'B':printf("12 Angry Man");
break;
case 'C':printf("Casabance");
break;
case 'D':printf("Blood Diamond");
}
}
答案 0 :(得分:6)
Casabance。
如果你有
char *cp;
int i;
然后cp[i] == *(cp+i) == *(i+cp) == i[cp]
。
C11 6.5.2.1:
后缀表达式后跟方括号[]中的表达式 是数组对象元素的下标。该 下标运算符[]的定义是E1 [E2]与...相同 (*((E1)+(E2)))。
和C11 6.5.6:
添加或减去具有整数类型的表达式时 从指针开始,结果具有指针操作数的类型。如果 指针操作数指向数组对象的元素和数组 足够大,结果指向一个偏离的元素 原始元素使得下标的差异 结果和原始数组元素等于整数表达式。
就编译器而言,字符串文字只是一个char指针。
彼此相邻的两个字符串文字自动连接成一个字符串文字:
C11 6.4.5:
在翻译阶段6中,指定的多字节字符序列 任何相邻字符序列和相同前缀字符串 文字标记连接成一个多字节字符 序列
所以... *(1+"AB" "CD"+1) == *(1+"ABCD"+1) == *("ABCD"+1+1)==*("BCD"+1) == "BCD"[1] == 'C'
。
答案 1 :(得分:3)
运行你的代码,你会得到答案“Casabance”
"AB" "CD"
等于"ABCD"
*("ABCD")
指向'A'
*("ABCD" + 0)
指向'A'
*("ABCD" + 1)
指向'B'
*("ABCD" + 2)
指向'C'
'C'
回答是“Casabance”答案 2 :(得分:1)
以下是不同步骤的说明,全部在编译时执行:
"AB" "CD"
在编译时连接成单个字符串文字"ABCD"
。char
的数组,使用值'A'
,'B'
,'C'
,'D'
和{{1}初始化}。'\0'
中,数组衰减为指向其第一个元素的指针,所述指针递增2指向第三个元素,在本例中为1 + "ABCD" + 1
字节。C
值char
。'C'
,转换为'C'
,尽管它不是C标准定义的常量表达式。int
优化为使用字符串switch
的{{1}}一次调用,因为可以在http://gcc.godbolt.org/#上验证请注意,示例中printf
的原型不正确,应为"Casabance"
或main
或等效。此外,在int main(void)
块的最后int main(int argc, char *argv[])
或break;
子句的末尾省略case
是容易出错的。