一、自增自减运算符
1. 基本用法
c
int a = 5; int b; b = a++; // 先赋值后自增:b=5, a=6 b = ++a; // 先自增后赋值:a先变成7, b=7
2. 指针与自增自减
c
int arr[] = {1, 2, 3}; int *p = arr; printf("%d\n", *p++); // 输出1,p指向arr[1] printf("%d\n", (*p)++); // 输出2,arr[1]变成3 printf("%d\n", *++p); // p先指向arr[2],输出33. 注意事项
副作用:自增自减会改变操作数的值
优先级:后缀
++/--> 前缀++/--> 解引用*求值顺序:避免在同一个表达式中对同一变量多次自增自减
二、赋值运算符
1. 基本赋值
c
int a = 10; // 简单赋值 a += 5; // 等价于 a = a + 5 a *= 2; // 等价于 a = a * 2
2. 复合赋值运算符
| 运算符 | 等价形式 | 说明 |
|---|---|---|
+= | a = a + b | 加赋值 |
-= | a = a - b | 减赋值 |
*= | a = a * b | 乘赋值 |
/= | a = a / b | 除赋值 |
%= | a = a % b | 模赋值 |
3. 多重赋值
c
int a, b, c; a = b = c = 10; // 从右向左赋值
三、关系运算符
1. 六种关系运算符
c
> // 大于 < // 小于 >= // 大于等于 <= // 小于等于 == // 等于 != // 不等于
2. 运算结果
结果为
1(真)或0(假)
c
int result = (5 > 3); // result = 1 result = (5 == 3); // result = 0
3. 注意事项
不要与赋值混淆:
=是赋值,==是比较浮点数比较:避免直接用
==比较浮点数,应使用误差范围
c
double x = 0.1 + 0.2; if (fabs(x - 0.3) < 1e-6) // 正确比较
四、逻辑运算符
1. 四种逻辑运算符
| 运算符 | 名称 | 说明 | 示例 | ||
|---|---|---|---|---|---|
&& | 逻辑与 | 两个都为真时结果为真 | (a>0 && b>0) | ||
| ` | ` | 逻辑或 | 至少一个为真时结果为真 | `(a>0 | b>0)` |
! | 逻辑非 | 取反操作 | !(a>0) | ||
| 按位逻辑 | 位运算 | 按位操作 | `&, | , ^, ~` |
2. 逻辑与&&和逻辑或||
c
int a = 5, b = 0; if (a > 0 && b > 0) // b>0为假,整体为假(短路特性) if (a > 0 || b > 0) // a>0为真,整体为真(短路特性)
3. 短路特性
c
int a = 0; int b = 5; if (a != 0 && b / a > 2) // a!=0为假,后面不会执行,避免除零错误 if (a == 0 || b / a > 2) // a==0为真,后面不会执行
4. 位逻辑运算符(按位操作)
c
unsigned int a = 5; // 0101 unsigned int b = 3; // 0011 a & b; // 0001 = 1 (按位与) a | b; // 0111 = 7 (按位或) a ^ b; // 0110 = 6 (按位异或) ~a; // 1010 = ... (按位取反)
5. 运算符优先级总结
从高到低:
()括号++ --后缀++ --前缀、!、~、+(正)、-(负)*、/、%+、-<、<=、>、>===、!=&(位与)^(位异或)|(位或)&&||=、+=、-=等赋值运算符
五、综合示例
c
#include <stdio.h> int main() { int a = 5, b = 3, c = 0; // 自增与关系运算 printf("a++ > b: %d\n", a++ > b); // 5>3为真,输出1,a变成6 // 逻辑运算 printf("a>0 && b>0: %d\n", a>0 && b>0); // 1 // 赋值与运算 c = a += 2; // a先加2变成8,再赋值给c printf("a=%d, c=%d\n", a, c); // a=8, c=8 return 0; }六、常见易错点
混淆
=和==c
if (a = 5) // 总是真,因为赋值表达式值为5 if (a == 5) // 正确比较
自增自减的顺序问题
c
int a = 5; int b = a++ + ++a; // 结果依赖编译器,避免这样写
短路特性的利用
用于条件判断中的函数调用保护
c
if (p != NULL && p->data > 0) // 避免空指针访问
位运算与逻辑运算的区别
c
int a = 1, b = 2; a & b; // 位运算:0 a && b; // 逻辑运算:1(非零为真)
总结:掌握这些运算符的优先级、结合性和特殊行为,是编写正确、高效C程序的基础。特别要注意自增自减的副作用和逻辑运算符的短路特性。