Pav*_*kin 2 c math macros c-preprocessor
问题:如何实现一个E扩展为整数常量表达式的宏,以便......
(E != (X) && E != (Y) && E != (Z))
Run Code Online (Sandbox Code Playgroud)
X...对于、Y、 和Z作为具有不同非负值的整数常量表达式的每个选择,其计算结果为 1 ?
例子:
#define X 13
#define Y 45
#define Z 76
#define E FUNC(X,Y,Z)
#define FUNC(X,Y,Z) ??
E /* evaluates to any number distinct from all of 13, 45, and 76 */
Run Code Online (Sandbox Code Playgroud)
使用哪个公式?有任何想法吗?
给定任意 3 个数字
X、Y和Z,生成一个int与所有 3 个值都不同的常数。
显然0, 、1、2或3必须满足标准。所以这里有一个解决方案:
#define FUNC(x,y,z) (((x) != 0 && (y) != 0 && (z) != 0) ? 0 : \
((x) != 1 && (y) != 1 && (z) != 1) ? 1 : \
((x) != 2 && (y) != 2 && (z) != 2) ? 2 : 3)
Run Code Online (Sandbox Code Playgroud)
这是一个更微妙的解决方案,根据每个参数的最后 2 位计算 、 或 ,但仅计算0参数1一次2:3
#define FUNC(x,y,z) ((int)((0x10201030102010 >> \
(4 * ((1 << ((x) & 3)) | \
(1 << ((y) & 3)) | \
(1 << ((z) & 3))))) & 3))
Run Code Online (Sandbox Code Playgroud)
解释:
4并将幻数移动0x10201030102010相应数量,然后掩码乘以 3 以选择与所有余数不同的值。可读性较差的版本将乘以2并移位0x484C484,仅使用 32 位算术:
#define FUNC(x,y,z) ((int)((0x484C484 >> ((2 << ((x) & 3)) | \
(2 << ((y) & 3)) | \
(2 << ((z) & 3)))) & 3))
Run Code Online (Sandbox Code Playgroud)