操作符和表达式

操作符和表达式

算术操作符(常用)

    +    -    *    /    %

注意:

    • — * /均可以作用于整数和浮点数。
  1. 对于/操作符如果两个操作数都为整数,执行整数除法。而只要有浮点数执行的就是浮点数除法。
  2. %操作符的两个操作数必须为整数。返回的是整除之后的余数。

移位操作符

左移运算符(<<)

规则:
  按二进制形式把所有的数字向左移动对应的位数,高位移出(舍弃),低位的空位补零。

例: 3 << 2
计算过程:
-w600

数学意义:
        在数字没有溢出的前提下,对于正数和负数,左移一位都相当于乘以2的1次方,左移n位就相当于乘以2的n次方。

右移运算符(>>)

规则:
        按二进制形式把所有的数字向右移动对应位移位数,低位移出(舍弃),高位的空位补符号位,即正数补零,负数补1。

例1:11 >> 2
计算过程:
-w600

例2:-7 >> 2
计算过程:
-w520

数学意义:
右移一位相当于除2,右移n位相当于除以2的n次方。

注意:移位操作符不能移动负数位

位操作符

& :按位与(相同位置只有都为1才为1)
| :按位或(相同位置要有一个位为1就为1)
^ :按位异或(相同位置相同为0,不同则为1)
注意:他们的操作数都必须是整数,按位故而需要按照整数的二进制每位操作,

应用

1.求一个整数二进制中1的个数?

//方法一
int CountOfNum1(int num)
{
	int count = 0;
	while (num > 0)
	{
		if (num % 2 == 1)
			count++;
		num = num / 2;
	}
	return count;
}
//方法二
int CountOfNum2(int num)
{
	int count = 0;
	int i = 0;
	for (i = 0; i < 32; ++i)
	{
	   //把每一位右移到最右边和1按位与,统计1出现的次数
		if (((num >> i)&1) == 1)
		{
			count++;
		}
	}
	return count;
}
//方法三(最优)
int CountOfNum3(int num)
{
	int count = 0;
	while (num)
	{
		count++;
		num = num&(num - 1);
	}
	return count;
}

2.不能创建临时变量(第三个变量),实现两个数的交换

int main()
{
	int a = 10;
	int b = 20;
	//利用异或性质中间导了一遍
	a = a^b;
	b = a^b;
	a = a^b;
	printf("a = %d  b = %d\n", a, b);
	system("pause");
	return 0;
}

赋值操作符

简单赋值

赋值操作符比较简单,就是给变量赋值,比较常见的就是我们在对一个已经被赋值的变量进行修改,直接将这个变量直接赋值成你想要的
例如:

int a = 0;
a = 10;

复合赋值

+=         -=         /=         *=         %=         >>=         <<=         &=         |=    等等

单目操作符

操作符 名称
逻辑反操作符
  • |负号
  • |正号
    & |取地址
    -- |自减
    ++ |自增
    ~ |按位取反
  • |解引用、间接访问
    sizeof |类型长度
    (类型) |强制类型转换

注意:结合使用时一定要搞清楚优先级,如果不清楚,手动加上括号来控制

关系操作符

符号 名称

|大于
=|大于等于
<|小于
<= |小于等于
== |等于等于
!= |不等于

int main()
{
    int a = 3;
    printf("%d", a += a-= a * a);
    return 0;
}

输出结果
-12
做题思路:
由于每次都需要将后面的值算出来才能进行-=和+=,故此题是按照从右向左计算的,为了方便理解,我们可以拆分计算
a += (a -= a*a)    a -= (a*a)     b = a*a=9
a -= (a*a)--> a -= b---> a = -6(注意此时a的值已经是6了,后面运算时a的值都以6计算)
a += (a -= a*a)---> a += a ---> -6+(-6)=-12

逻辑操作符

&& 逻辑与(“并且”):两个操作数都为真,结果才为真
||    逻辑或(“或者”):所有操作数都为假时才为假,有一个或者多个操作数为真就为真

注意:区分逻辑与/或 和 按位与/或的区别

#include <stdio.h>
int main() {
       int i = 0,a=1,b=2,c =3,d=4;
       i = a++&&++b&&d++;
       //i = a++||++b||d++;
       printf("a = %d\n b = %d\n c = %d\nd = %d\n", a, b, c, d);
       return 0;
}

输出结果
    2,3,3,5
//  2,2,3,4

条件操作符

A ? B : C --- 三元运算符
在某些场景下可以替代if else语句

if(y > 0)
    x = 1;
else
    x = 0;

以上代码等同于下段代码

( y > 0) ? x = 1 : x = 0;

逗号表达式

将两个及以上的式子连接起来,整个表达式的值是最后一个表达式的值

  1. 从左到右依次计算
  2. 最终值是表达式中最后一个表达式的值
  3. 所有运算符中优先级最低的

例:

int main()
{
    int i = 1;
    int j = 1;
    int z = 0;
    z = i++,j++,++j;
    //z = (i++,j++,++j);
    printf("i=%d j=%d z=%d",i,j,z);
    return 0;
}

输出结果
    2,3,1
//  2,3,3
解题思路:
z = i++,j++,++j;因为=的优先级要高于逗号表达式,所以原式等于(z = i++),j++,++j;
因为后置加加先使用后加加,所以z=1,i=2,j++时j为1,当走到j++后面的,时j已经变成2,++j后就成了3。

同理 z = (i++,j++,++j);()的优先级高于=,所以先算()里的逗号表达式,再算=,所以z=3。

某些场景逗号表达式也可以使表达简洁

    //while(a > 0)
    //{
    //    a = test();
    //    a++;
    //}
    //等价上面代码
    while(a = test(), a++, a > 0)

下标引用、函数调用和结构成员

符号 功能
[] 数组访问
() 函数调用
. 结构体/类 访问成员
-> 结构体/类 指针访问成员
posted @ 2018-07-26 10:43  竹杖芒鞋鲜衣怒马  阅读(254)  评论(0编辑  收藏  举报