C maximal munch strategy (最大一口策略) -
c = a+++b;
<==>
c = a++ + b;
c = a+++b;
<==>
c = a++ + b;
1. c = a+++b;
<==> c = a++ + b;
c = a+++b;
等同于
c = a++ + b;
对于 c = a+++b;
语句,程序员的意图可能是 c = a + ++b;
,也可能是 c = a++ + b;
。
ANSI C
规定了一种逐渐为人所熟知的 maximal munch strategy
(最大一口策略)。这种策略表示如果下一个标记有超过一种的解释方案,编译器将选取能组成最长字符序列的方案。c = a+++b;
将被解析为 c = a++ + b;
。
munch [mʌntʃ]:vt. 用力咀嚼,大声咀嚼 vi. 用力咀嚼,大声咀嚼 n. 用力的咀嚼
1.1 Example
//============================================================================
// Name : main
// Author : Yongqiang Cheng
// Version : Version 1.0.0
// Copyright : Copyright (c) 2019 Yongqiang Cheng
// Description : Hello World in C++, Ansi-style
//============================================================================
#include <stdio.h>
int main(int argc, char *argv[])
{
int a = 0, b = 0, c = 0, d = 0;
printf("argc = %d\n", argc);
for (int idx = 0; idx < argc; ++idx)
{
printf("argv[%d] --> %s\n", idx, argv[idx]);
}
printf("argv[argc] = %p\n\n", (void*)argv[argc]);
a = 3;
b = 6;
c = 0;
c = a+++b;
printf("c = a+++b; => c = %d\n", c);
printf("a = %d\n", a);
printf("b = %d\n\n", b);
a = 3;
b = 6;
d = 0;
d = a++ + b;
printf("d = a++ + b; => d = %d\n", d);
printf("a = %d\n", a);
printf("b = %d\n\n", b);
return 0;
}
argc = 1
argv[0] --> D:\visual_studio_workspace\yongqiang\Debug\yongqiang.exe
argv[argc] = 00000000
c = a+++b; => c = 9
a = 4
b = 6
d = a++ + b; => d = 9
a = 4
b = 6
请按任意键继续. . .
1.2 Example
//============================================================================
// Name : main
// Author : Yongqiang Cheng
// Version : Version 1.0.0
// Copyright : Copyright (c) 2019 Yongqiang Cheng
// Description : Hello World in C++, Ansi-style
//============================================================================
#include <stdio.h>
int main(int argc, char *argv[])
{
int a = 0, b = 0, c = 0, d = 0;
printf("argc = %d\n", argc);
for (int idx = 0; idx < argc; ++idx)
{
printf("argv[%d] --> %s\n", idx, argv[idx]);
}
printf("argv[argc] = %p\n\n", (void*)argv[argc]);
a = 3;
b = 6;
c = 0;
printf("a = %d\n", a);
printf("b = %d\n", b);
printf("c = %d\n", c);
c = a+++b;
printf("c = a+++b; => c = %d\n", c);
printf("a = %d\n", a);
printf("b = %d\n\n", b);
a = 3;
b = 6;
d = 0;
printf("a = %d\n", a);
printf("b = %d\n", b);
printf("d = %d\n", d);
d = a++ + b;
printf("d = a++ + b; => d = %d\n", d);
printf("a = %d\n", a);
printf("b = %d\n\n", b);
return 0;
}
argc = 1
argv[0] --> D:\visual_studio_workspace\yongqiang\Debug\yongqiang.exe
argv[argc] = 00000000
a = 3
b = 6
c = 0
c = a+++b; => c = 9
a = 4
b = 6
a = 3
b = 6
d = 0
d = a++ + b; => d = 9
a = 4
b = 6
请按任意键继续. . .
2. c = a+++++b;
<!=> c = a++ + ++b;
c = a+++++b;
按照前面的策略将被解析为 c = a++ ++ + b;
,这将引起一个编译错误,错误信息是 ++ 操作符迷失于空格间
。即使编译器能够推断 (从理论上说) 惟一有效的编排方式是 c = a++ + ++b;
,它还是会出现编译错误。
2.1 error C2105: '++' needs l-value
//============================================================================
// Name : main
// Author : Yongqiang Cheng
// Version : Version 1.0.0
// Copyright : Copyright (c) 2019 Yongqiang Cheng
// Description : Hello World in C++, Ansi-style
//============================================================================
#include <stdio.h>
int main(int argc, char *argv[])
{
int a = 0, b = 0, c = 0;
printf("argc = %d\n", argc);
for (int idx = 0; idx < argc; ++idx)
{
printf("argv[%d] --> %s\n", idx, argv[idx]);
}
printf("argv[argc] = %p\n\n", (void*)argv[argc]);
a = 3;
b = 6;
c = 0;
printf("a = %d\n", a);
printf("b = %d\n", b);
printf("c = %d\n", c);
c = a+++++b;
printf("c = a+++++b; => c = %d\n", c);
printf("a = %d\n", a);
printf("b = %d\n\n", b);
return 0;
}
1>------ Rebuild All started: Project: yongqiang, Configuration: Debug Win32 ------
1> foreverstrong.c
1>d:\visual_studio_workspace\yongqiang\yongqiang\foreverstrong.c(32): error C2105: '++' needs l-value
========== Rebuild All: 0 succeeded, 1 failed, 0 skipped ==========
2.2 c = a++ + ++b;
//============================================================================
// Name : main
// Author : Yongqiang Cheng
// Version : Version 1.0.0
// Copyright : Copyright (c) 2019 Yongqiang Cheng
// Description : Hello World in C++, Ansi-style
//============================================================================
#include <stdio.h>
int main(int argc, char *argv[])
{
int a = 0, b = 0, c = 0;
printf("argc = %d\n", argc);
for (int idx = 0; idx < argc; ++idx)
{
printf("argv[%d] --> %s\n", idx, argv[idx]);
}
printf("argv[argc] = %p\n\n", (void*)argv[argc]);
a = 3;
b = 6;
c = 0;
printf("a = %d\n", a);
printf("b = %d\n", b);
printf("c = %d\n", c);
c = a++ + ++b;
printf("c = a+++++b; => c = %d\n", c);
printf("a = %d\n", a);
printf("b = %d\n\n", b);
return 0;
}
argc = 1
argv[0] --> D:\visual_studio_workspace\yongqiang\Debug\yongqiang.exe
argv[argc] = 00000000
a = 3
b = 6
c = 0
c = a+++++b; => c = 10
a = 4
b = 7
请按任意键继续. . .