IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> C++知识库 -> C语言操作符 -> 正文阅读

[C++知识库]C语言操作符

目录

1.算数操作符

2.移位操作符

3.位操作符

4.赋值操作符

5.单目操作符

6.关系操作符

7.逻辑操作符

8.条件操作符

9.逗号表达式

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

11.隐式转换*


插曲:符号位也是参与运算的。

1.算数操作符

+? ? -? ?*? ? /? ?%

1.除了%操作符之外,其他的几个操作符可以作用于整数和浮点数。

2.对于 / 操作符如果两个操作数都为整数,执行整数除法。而只要有浮点数执行的就是浮点数除法。

两个整数除,最终结果还是整数double打印也是4.000000。

为什么打印的不是4.500000,所以把2改成2.0就成为了浮点数。

3.% 操作符的两个操作数必须为整数。返回的是整除后的余数。

2.移位操作符

<< 左移操作符

>> 右移操作符

注意:移位操作符移动的是二进制位(二进制补码)。

左移操作符移位法则:

左边抛弃,右边补0

右移操作符移位法则:

首先右移运算分为两种:

1.逻辑移位:左边用0填充,右边丢弃

2.算术移位:左边使用原该值的符号位填充,右边丢弃。

3.位操作符

& 按位与

| 按位或

^ 按位异或?

注意:它们的操作数必须是整数。符号位也参与运算。

异或的题目:异或具有交换律

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

#include <stdio.h>

int main()
{
	int a = 5;
	int b = 10;
	a = a ^ b;
	b = a ^ b;
	a = a ^ b;
	printf("a=%d  b=%d", a, b);
	return 0;
}

4.赋值操作符

=

赋值操作符可以连续使用:

int main()
{
	int a = 10;
	int x= 0;
	int y = 20;
	a = x = y + 1;
	return 0;
}

等价于:

int main()
{
	int a = 10;
	int x= 0;
	int y = 20;
	x = y + 1;
	a = x;
	return 0;
}

复合赋值符?

+= 、-=、*=、/=、%=、>>=、<<=、&=、|=、^=

int x = 10;
x = x + 10;
//这两句等价上边符合运算符也是如此
x += 10;

5.单目操作符

! 逻辑取反

-? ?负值

+? ?正值

&? ?取地址

sizeof? 操作数的类型长度(以字节位单位)

~? ?对一个数的二进制按位取反(取反符号位也参与运算)

--? 前置、后置--

++ 前置、后置++

*? 间接访问操作符(解引用操作符)

(类型)?强制类型转换

说明一下:左值和右值问题

左值:一般就是使用变量的空间

右值:一般就是指空间的内容

1.sizeof

sizeof是计算变量或者类型创建变量的内存大小,和内存中存放什么数据没有关系,sizeof是一个操作符,不是函数。

证明sizeof不是函数

int main()
{
	int a = 10;
	printf("%d",sizeof(a));
	printf("%d", sizeof a);
	return 0;
}

结果都是4,4个字节.?

sizeof代码分析:

int main()
{
	int a = 10;
	printf("%d\n",sizeof(a=a+10));
	printf("%d",a);
	return 0;
}

结果:?

sizeof内表达式不参与运算,编译阶段就已经计算好了,不进行链接。因此a=a+10不执行,直接算变量的内存大小所以位4,10。

sizeof和数组

void test1(int arr[])
{
	printf("%d\n", sizeof(arr));
}
void test2(char ch[])
{
	printf("%d\n", sizeof(ch));
}
int main()
{
	int arr[10] = { 0 };
	char ch[10] = { 0 };
	printf("%d\n", sizeof(arr));
	printf("%d\n", sizeof(ch));
	test1(arr);
	test2(ch);
	return 0;
}

结果:

首先40和10:数组单独放在sizeof内部时,数组名表示整个数组,计算整个数组的大小。

4和4:函数中数组的传参,其实只是传进去了指针,int arr[]==int* arr。地址的大小4/8个字节。

2.强制类型转换

强制类型转换的意义:保证前后数据类型的一致,防止警告。

int a=3.14;

会出现警告,为了保证前后数据类型一致性,并取消掉警告,需要使用强制类型转换。

int a=(int)3.14;

这样就不会出现警告了。

6.关系操作符

>、>=、<、<=、!=、==?

这里就只需要注意:==别写成=,说多了都是泪。

7.逻辑操作符

&& 逻辑与

||? ?逻辑或

区分按位与&、或 ||和逻辑与&&、或||

代码分析:

int main()
{
	int i = 0, a = 0, b = 2, c = 3, d = 4;
	i = a++ && ++b && d++;

	printf("a = %d\n b = %d\n c = %d\nd = %d\n", a, b, c, d);
	return 0;
}

结果:?

首先在执行 i = a++ && ++b && d++;?时,a时后置++先使用在++;因此在a在&&的的时候是0,逻辑与一个为假,结果为假,当为假的时候后面就不在执行。所以结果为1,2,3,4

int main()
{
	int i = 0, a = 0, b = 2, c = 3, d = 4;

	i = a++||++b||d++;

	printf("a = %d\n b = %d\n c = %d\nd = %d\n", a, b, c, d);
	return 0;
}

这个代码与上边的代码正好是相反的,当为真时停止后边的计算,a后置++,所以a在执行||时为0,a在++ a=1;继续执行++b 前置++,x先++在使用,b++等于3为真,因此结果为 1 3 3 4.?

8.条件操作符

exp1 ? exp2 : exp3 //C语言唯一个三目操作符

exp1表达式是否成立,成立结果为exp2,否则为exp3。

9.逗号表达式

exp1,exp2,exp3,....expN

逗号表达式,就是用逗号隔开的多个表达式。逗号表达式,从左向右依次执行。整个表达式的结果是最后一个表达式的结果。

代码分析:

int main()
{
	int a = 1;
	int b = 2;
	int c = (a > b, a = b + 10, b = a + 1);
	printf("%d\n",a);
	printf("%d\n",b);
	printf("%d\n",c);
}

逗号表达式应用的意义:?

a = get_val();
count_val(a);
while (a > 0) {
 ? ?     //业务处理
 ? ? ? ?a = get_val();
 ? ? ? ?count_val(a);
}

等价于
while (a = get_val(), count_val(a), a>0) {
 ? ? ? ? //业务处理
}
if (a =b + 1, c=a / 2, d > 0)

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

1.[ ]下标引用操作符

操作数:一个数组名+一个索引值

int arr[10];

[ ]操作符是arr和9.

2.()函数调用操作符

接受一个或者多个操作数:第一个操作数是函数名,剩余的操作数就是传递给函数的参数。

3.访问一个结构成员

结构体.成员名

(结构体指针)->成员名

都是操作符。。。

11.隐式转换*

表达式求值的顺序一部分是由操作符的优先级和结合性决定。有些表达式的操作数在求值过程中可可能需要转换为其他类型。

1.整型提升

在C语语言中,C的整型算术运算总是至少以缺省(默认)整型类型的精度来进行的。为了获得这个精度,表达式中的字符和短整型操作数在使用之前都被转换围殴普通的整型(int),这种转换称为整型提升。(其实整型提升主要针对的是short和char。)

整型提升的意义:

表达式的整型运算要在CPU的相应运算器件内执行,CPU内整型运算器(ALU)的操作数的字节长度一般就是int的字节长度,同时也是CPU通用寄存器的长度。因此即便是两个char类型相加,在CPU执行时实际上也要先转换为CPU内整型操作数的标准长度(整型提升)。通用CPU是难以直接实现两个8比特字节直接相加运算。所以,表达式中各种长度可能小于int长度的整型值,都必须先转换位int或unsinged int ,然后才送入CPU去执行运算。

整型提升代码分析:

#include <stdio.h>

int main()
{

	char a = -2;
	char b = 1;
	char c = a + b;
	printf("%d\n",c);
	return 0;
}

?注意:无符号的整型提升,高位补0;

整型提升的例子:

#include <stdio.h>

int main()
{
	char a = 0xb6;
	short b = 0xb600;
	int c = 0xb6000000;
	if (a==0xb6)
	{
		printf("a");
	}
	if (b == 0xb600)
	{
		printf("b");
	}
	if (c == 0xb6000000)
	{
		printf("c");
	}
}

结果:

其实当进行操作符进行各类计算时,都会发生整型提升的隐式转换。也就是说这里的在进行==号进行操作符运算时,会发生整型提升,其实这个整型提升是需要看后面的==后面比较的数是否为整型。个人理解就是:需不需要整型提升是需要看操作符各个操作数属不属于相同类型,如果不属于就转换成层次体系高的:也就是所谓的算术转换。

2.算术转换

如果每个操作符的各个操作数属于不同的类型,那么除非其中一个操作数转换为另一个操作数的类型,否则操作就无法进行。下面是层次体系称为寻常算术转换

#include <stdio.h>

int main()
{
	float i = 3.14;
	int num = i;
}

这里发生了截断数据,直接把3.14截断成整数3进行存储。所以有时算术转换要合理,要不然后发生一些潜在的问题。

3.操作符的属性:

复杂表达式的求值有三个影响的因素.

1.操作符的优先级(只决定相邻的操作符,相邻的操作符看优先级)

2.操作符的结合性。

3.是否控制求值顺序,也就是所说的: &&? ?||

根据操作符优先级:

一些问题表达式:这些问题需要小心且避免。

1.

a*b+c*d+e*f

根据优先级,*比+的优先级高,所以相邻的还是先算*再算加,但是会出现2中情况:

第一种是先算完乘法在进行+法,都满足优先级。

a*b

c*d

e*f

a*b+c*d+e*f

第二种是也是先算的*,也满足优先级

a*b

c*d

a*b+c*d

e*f

a*b+c*d+e*f

上述两种情况都满足优先级,但是无法确定第一个+先执行还是最后一个*先执行,所以程序存在二义性。

2.

C+ --C

首先 -- 的优先级比+的优先级高,先执行--,但是我们无法知道第一个c的值是取--c之前还是之后呢。

3.

#include <stdio.h>

int main()
{
	int i = 1;
	int ret = (++i) + (++i) + (++i);
	printf("%d\n",ret);
	
}

这段代码在linux中是10,在windows中是12。所以程序有二义性。

分析windows汇编了解一下在windows中的过程:

?也就是 ++i 执行完成后在执行+。在Linux中执行过程就不一样。

4.

#include <stdio.h>

int fun()
{
	static int count = 1;
	return ++count;
}
int main()
{
	int answer;
	answer = fun() - fun() * fun();
	printf("%d\n", answer);
	return 0;
}

这段代码大部分编译器都是:-10,但是这段代码也有二义性,虽然 * 比 - 的优先级高,但是根本无法知道是 fun() 函数调用的先后顺序。

总结:可以建立多个变量或分开写,避免出现这种错误代码。

  C++知识库 最新文章
【C++】友元、嵌套类、异常、RTTI、类型转换
通讯录的思路与实现(C语言)
C++PrimerPlus 第七章 函数-C++的编程模块(
Problem C: 算法9-9~9-12:平衡二叉树的基本
MSVC C++ UTF-8编程
C++进阶 多态原理
简单string类c++实现
我的年度总结
【C语言】以深厚地基筑伟岸高楼-基础篇(六
c语言常见错误合集
上一篇文章      下一篇文章      查看所有文章
加:2022-01-08 13:48:12  更:2022-01-08 13:50:41 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 11:47:46-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码