C中的&
和&&
有什么区别?
我的老师给了我这个例子:
int a = 8;
int b = 4;
printf("a & b = %d\n", a & b);
printf("a && b = %d\n", a && b);
输出:
a & b = 0;
a && b = 1;
我不确定为什么这会在一个场景中返回true而在另一个场景中返回false。
答案 0 :(得分:7)
&
按位且且&&
逻辑且。
如果x && y
和1
都不为零,则表达式x
将返回y
,否则将0
。请注意,如果x
为零,则根本不会评估y
。
表达式x & y
将对x
和y
中的每个位执行按位运算。因此,如果x
为1010
二进制且y
为1100
,则x & y
将评估为1000
。请注意,x & y
的返回值不应解释为布尔值。
解释它的一种方法是,您可以想象&
与在操作数中的每个位上应用&&
相同。
另请注意,&
的优先级低于&&
,即使直觉说它应该是另一种方式。这也适用于比较运算符,例如<
,<=
,==
,!=
,>=
,>
。这可以追溯到C没有运算符&&
和||
并且使用了按位版本的时间。在这个时候,它是有道理的,但是当添加逻辑运算符时,它就不再存在了。 Kernighan和Ritchie承认它会更有意义,但他们没有修复它,因为这会破坏现有的代码。
我不确定为什么这会在一个场景中返回true而在另一个场景中返回false。
来自x & y
的返回值 not 根本不会被视为布尔值。但是,它可以(取决于代码的编写方式)被视为布尔数组。如果您有两个整数flags1
和flags2
,则flags1 & flags2
的结果将表示在中切换的标记 flags1
和{{ 1}}。
答案 1 :(得分:2)
<强>&安培;&安培; (逻辑和运算符) - 左右操作数是
boolean
个表达式。 如果两个操作数均为非零,则条件成立。
&GT;
<强>&安培; (按位和运算符) - 左右操作数是
integral
类型。如果它存在于两个操作数中,则二进制AND运算符将一点复制到结果中。
在教师的示例a && b
中,左操作数4
和右操作数8
均为非零。所以情况会变成现实。
在教师的其他示例a & b
中,左操作数4
或0100
和右操作数8
或01000
不会复制任何位结果。这是因为在任一操作数中都没有公共的设置位。
答案 2 :(得分:1)
&
运算符对其整数操作数执行按位和运算,从而产生整数结果。因此(8 & 4)
为(0b00001000 bitand 0b00000100)
(为了清晰起见,使用标准C中不存在的二进制表示法),这会产生0b00000000
或0
。
&&
运算符对其布尔操作数执行逻辑和运算,从而产生布尔结果。因此,(8 && 4)
相当于((8 != 0) and (4 != 0))
或(true and true)
,从而产生true
。