C语言:操作符详解1


一.操作符的分类

c 复制代码
算术操作符:+、-、* 、 /、%
移位操作符:<<   >>
位操作符:&   |    ^
赋值操作符:= 、+=、-=、*=、/=、%=、<<=、>>=、&=、|=、^=
单目操作符:!、++、--、&、*、+、-、~、sizeof、(类型)
关系操作符:>、>=、<、<= 、== 、!=
逻辑操作符:&&、|| 
条件操作符:? :
逗号表达式:,
下标引用:[]
函数调用:()
结构成员访问:、. ->
上述的操作符,我们之前已经讲过算术操作符、赋值操作符、逻辑操作符、条件操作符和部分的单目操作符,今天继续介绍一部分,操作符中有一些操作符和二进制有关系,我们先铺垫一下二进制的和进制转换的知识。

二.二进制和进制转换

其实我们经常能听到 2进制、8进制、10进制、16进制 这样的讲法,那是什么意思呢?其实2进制、8进制、10进制、16进制是数值的不同表示形式而已。比如:数值15的各种进制的表示形式:

c 复制代码
15的2进制:1111
15的8进制:17
15的10进制:15
15的16进制:F
16进制的数值之前写:0x
8进制的数值之前写:0

我们来写代码看一看:

我们重点介绍一下二进制:

首先我们还是得从10进制讲起,其实10进制是我们生活中经常使用的,我们已经形成了很多常识:

c 复制代码
10进制中满10进1
10进制的数字每一位都是0~9的数字组成
其实二进制也是一样的
2进制中满2进1
2进制的数字每一位都是0~1的数字组成
那么 1101就是二进制的数字了。

1.二进制转10进制

其实10进制的123表示的值是一百二十三,为什么是这个值呢?其实10进制的每一位是有权重的,10进制的数字从右向左是个位、十位、百位......,分别每一位的权重是10,101,102...

如下图:

2进制和10进制是类似的,只不过2进制的每一位的权重,从右向左是:2,21,22...

T如果是2进制的1101,该怎么理解呢?

2.10进制转2进制数字

数字大的可以这样算,数字小的没必要,比如我们可以这样算:

3.二进制转8进制和16进制

二进制转8进制

8进制的数字每一位是0~7的,0~7的数字,各自写成2进制,最多有3个2进制位就足够了,比如7的二进制是111,所以在2进制转8进制数的时候,从2进制序列中右边低位开始向左每3个2进制位会换算一个8进制位,剩余不够3个2进制位的直接换算。

2.2 2进制转8进制和16进制

如:2进制的01101011,换成8进制:0153,0开头的数字,会被当做8进制。

二进制转16进制

16进制的数字每一位是0~9, a~f 的,0~9, a~f的数字,各自写成2进制,最多有4个2进制位就足够了,比如f的二进制是1111,所以在2进制转16进制数的时候,从2进制序列中右边低位开始向左每4个2进制位会换算一个16进制位,剩余不够4个二进制位的直接换算。

如:2进制的01101011,换成16进制:0x6b,16进制表示的时候前面加0x。


三.原码、反码、补码

整数的2进制表示方法有三种,即原码、反码和补码 。有符号整数的三种表示方法均有符号位和数值位 两部分,2进制序列中,最高位的1位是被当做符号位 剩余的都是数值位。符号位都是用0表示"正",用1表示"负"。

c 复制代码
正整数的原、反、补码都相同。
负整数的三种表示方法各不相同。

我们来画个图看一下:

我们来看个例子:

根据这个数字的正负直接写出的二进制序列叫它的原码。

来看相关概念:

c 复制代码
原码:直接将数值按照正负数的形式翻译成二进制得到的就是原码。
反码:将原码的符号位不变,其他位依次按位取反就可以得到反码。
补码:反码+1就得到补码。

补码得到原码也是可以使用:取反,+1的操作。

我们把例子补全来看:

我们画图来看原码、反码、补码的转换关系:

例子:

对于整形来说:数据存放内存中其实存放的是补码

为什么呢?

在计算机系统中,数值一律用补码来表示和存储。原因在于,使用补码,可以将符号位和数值域统一处理;同

时,加法和减法也可以统一处理(CPU只有加法器)此外,补码与原码相互转换,其运算过程是相同的,不需要额外的硬件电路。

我们直接画图来举例子


四.移位操作符

<< 和 >> 分别为左移操作符和右移操作符。注:移位操作符的操作数只能是整数。

1.左移操作符

移位规则:左边抛弃、右边补0。左移是移动的二进制序列。

来看例子:


我们要知道这样的左移操作不会改变num本身的值,但是会将产生的效果赋给n,如果想要改变num可以这样写:num<<=1。

我们再来举例一个负数:

从上面例子观察到向左移动一位有乘2的效果,但是不是对所有数字都适用。

2.右移操作符

右移到底是算术右移,还是逻辑右移,是取决于编译器的 ,但是大部分编译器采用的都是算术右移。

移位规则:首先右移运算分两种:

c 复制代码
1.逻辑右移左边用0填充,右边丢弃
2.算术右移:左边用原该值的符号位填充,右边丢弃


我们也来举一个负数的例子:

我们发现右移一位有除2的效果。

警告:对于移位运算符,**不要移动负数位,**这个是标准未定义的。

例如:

c 复制代码
1  int num  = 10;
2  num >>-1;//error

五.位操作符

位操作符有:&(按位与) |(按位或) ^(按位异或) ~(按位取反)

注:它们的操作数必须是整数。

我们直接来上代码:

两个补码按位与运算的时候,对应的二进制位相与,有0则为0,两个同时为1才为1。这样可得上面结果。

这是按位或操作,两个补码对应的二进制位或运算,有1则为1,有两个0才为0。

这是按位异或运算,两个补码对应的二进制序列它的规则是:相同为0,相异为1。

我们再来看按位取反运算

规则就是:补码的二进制序列,为1变为0,为0的变为1;

记住:这些操作符都是拿二进制位进行计算的。

相关推荐
多来米19961 小时前
小白学多线程(持续更新中)
java·开发语言
ZERO空白1 小时前
Spring MVC:原理、配置与基础应用详解
java·spring·mvc
zky___2 小时前
Android \android-sdk\platform-tools\adb.exe start-server‘ failed
android·adb
lb36363636362 小时前
strlwr(arr);的模拟实现(c基础)
c语言·知识点·c积累
冰零(lane)2 小时前
手写一个深拷贝工具
java
paterWang2 小时前
小程序-基于java+SpringBoot+Vue的流浪动物救助小程序设计与实现
java·spring boot·小程序
轮到我狗叫了4 小时前
栈的应用,力扣394.字符串解码力扣946.验证栈序列力扣429.N叉树的层序遍历力扣103.二叉树的锯齿形层序遍历
java·算法·leetcode
Reese_Cool4 小时前
【C++】从C语言到C++学习指南
c语言·c++·1024程序员节
小柯J桑_4 小时前
C++:探索AVL树旋转的奥秘
开发语言·c++·avl树