【C 初学--------操作符】

操作符

1.算术操作符

(1)、基本的操作的操作符


这几种基本的算术运算符,就不必介绍了

  1. 加号(+)
  2. 减号(-)
  3. 乘号(*)

(2)、除号(/)

除号的使用,求得的是商

eg:

#include<stdio.h>
int main()
{
	float c = 6.0/5.0;
	printf("%f",c);
	return 0;
}

上面的结果会出现 warning C4305: “=”: 从“double”到“float”截断

解决 float c = 6.0f / 5.0f;

(3)、取模(%)

取模操作符的两个操作数必须为整数,返回的是整除之后的余数。

#include<stdio.h>
int main()
{
	int c = 6/5;
	printf("%d",c);
	return 0;
}

2.移位操作符

(1)、 左移操作符(<<)

左移操作符 移位规则

左边抛弃,右边补0

代码如下:

#include<stdio.h>
int main()
{
	int c = 2;
	int a = c << 1;
	printf("%d",a);
	return 0;
}

算出来的结果为 4

因为四个字节 所以2的二进制码为:-00000000000000000000000000000010,
000000000000000000000000000000100

(2)、 右移操作符(>>)

右移操作符 移位规则

右边抛弃,左边补0

代码如下:

#include<stdio.h>
int main()
{
   int c = 2;
   int a = c >> 1;
   printf("%d",a);
   return 0;
}

算出来的结果为:1

由上可得 00000000 00000000 00000000 00000010
------ – —00000000000000000000000000000000010

右移操作符分为:
1.算术右移

右边丢弃,左边补原符号位

2.逻辑右移

右边丢弃,左边补0

大多数我们都是应用的都是算术右移

3.位操作符

  • 按位与(&)
  • 按位或(|)
  • 按位异或(^)

按位与,或,异或都是按照二进制来进行的

  • 与(&): 0 1为0,0 0为0,1 1为1
  • 或(|):0 1为1,0 0为0, 1 1为1
  • 异或(^):0 1为1,1 1为0,0 0为0

例如下面的例子:

#include<stdio.h>
int main()
{
   int a = 3;
   int b = 5;
   int c = a & b;
   int d = a | b;
   int e = a ^ b;
   printf("%d,%d,%d",c,d,e);
   return 0;
}

打印的结果为 1,7,6

因为a = 3的二进制位为- 0011,b的二进制位为- 0101
按照上面的原则就可以分别得到各种结果:

与(&):---------0001-------1
或(|):----------0111--------7
异或(^):------0110--------6

根据上面的原则有一道题非常有趣:

交换两个int 变量的值,不能使用第三个变量,即a = 3,b = 5,交换之后a = 5, b = 3;

这道题目我们就可以根据上面的原则就可以解决出来:

#include<stdio.h>
int main()
{
   int a = 3;
   int b = 5;
   a = a ^ b;
   b = a ^ b;
   a = a ^ b;
   printf("a = %d,b = %d",a,b);
   return 0;
}

打印的结果为:a = 5,b = 3

4.赋值操作符

(1)、简单的赋值操作符

例如:

int a = 10;
char ch = 'a';
float a = 3.0;

(2)、复合的赋值操作符

+= -= *= /= %= >>= <<= &= |= ^=
这些运算符都可以写成符合的效果。

#include<stdio.h>
int main()
{
   int a = 3;
   a = a + 4;
   printf("a = %d",a);
   return 0;
}
#include<stdio.h>
int main()
{
   int a = 3;
   a+ = 4;
   printf("a = %d",a);
   return 0;
}

这两种形式都是相同的结果

5.单目操作符

(1)、(!、 -、 + 、(类型))的应用

  • ! ------------逻辑反操作
  • - ------------负值
  • + -----------正值
  • &-----------取地址
  • (类型)----强制类型转化

1.逻辑反的使用(!)

if(a == 3) printf("我要学习!");

if(a != 3) printf("我不学习!");


2.减和加(- +)
int a= 3; a = - a;
int a = 4; a = + a;

+号一般都是省略掉


3.强制类型转化 --(类型)

int a = 5.21;		//这样就会报错
int a = (int)5.21;	//强制类型转化

(2)、(sizeof() 、~)的应用

1. sizeof

1 、计算某一类型或者变量的大小,单位是字节
2、sizeof是一个操作符,不是一个函数。
3、传递给数组的名后,计算的是整个数组的大小。
4、sizeof括号中的表达式是不参与运算的。
5、sizeof遇见数组传参
6、sizeof计算地址的大小的时候,4/8个字节。

	 int a = 3;
	printf("%d",sizeof(a));			//打印的结果为4
	int a = 3;
	printf("%d",sizeof(int));		//打印的结果为4
	int a[10] = { 0 };
	printf("%d",sizeof(arr));   //打印的结果为40
#include<stdio.h>
int main()
{	
	short a = 2;
	int b = 5;
	printf("%d",sizeof(a = b + 2)); //计算的结果为2
	printf("%d",a); a = 2
	return 0;
}

上面的原因是因为一个源文件(.c)成为一个可执行文件(.exe)需要经过:编译–链接—运行。
上面的式子 b + 2,是在运行期间才可以运行的,但是sizeof计算的大小的时候是在编译期间运算的,即在上面的大小仅仅取决于a,b + 2的式子没有参与运算。

#include<stdio.h>
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));	//40
	printf("%d\n",sizeof(ch));  //10
	test1(arr);  			    //8
	test2(ch);				    //8
	return 0;
}

上面的传参都是指针变量—在同一平台下他们的大小都是相同的

#include<stdio.h>
#include<string.h>
int main()
{
	char  arr[] = "xiao meng";
	printf("%d\n",sizeof(arr)); // 10
		//计算的是数组占空间的大小,后面的'\0'同样也计算在内
	printf("%d\n",strlen(arr));  // 9
	//计算'\0'前面的字符占的大小
	return 0;
}

strlen 函数的为**size_t strlen ( const char * str )**,即传给函数的是一个地址

	char arr[] = {'a','c','t','e'};
	printf("%d ",strlen(arr));//随机值
	printf("%d ",strlen(*arr));//报错
	printf("%d ",strlen(&arr));//随机值
	printf("%d ",strlen(&arr + 1));//随机值减4
	printf("%d ",strlen(&arr[0] + 1));//随机值减1,即从'c'开始往后面计算
	int arr[3][4] = { {1,3,5,4},{2,4,7,5},{5,6,8,7} };
	printf("%d \n", sizeof(arr));//48整个数组的大小 
	printf("%d \n", sizeof(arr + 1));//arr没有取地址,也没有单独的放在sizeof中,
									//arr就表示数组首地址,即第一行地址,arr + 1即为第二行地址
									
	printf("%d \n", sizeof(*(arr + 1)));//第二行元素大小
	//*(arr + 1)拿到的是整个第二行地址,*(*(arr + 1))是第二行第一个元素
	printf("%d \n", sizeof(*arr));//没有取地址,也没有单独的放在sizeof中,
			//arr表示数组首地址即第一行地址,*arr即表示第一行元素的大小

	printf("%d \n", sizeof(arr[0]));//表示第一行的元素的大小
	printf("%d \n", sizeof( *(arr[0] + 1) ));//表示第一行第一个元素
											//和arr[0][0]表示的方法相同
	printf("%d \n", sizeof(&arr[0] + 1) );第二行的地址
	printf("%d \n", sizeof( *(&arr[0] + 1) ));第二行元素的大小
	printf("%d \n", sizeof(arr[0] + 1));// arr[0]没有单独放在sizeof中,也没有取地址,
	//即为第一行第一个元素的地址
	printf("%d \n", sizeof(arr[0][0]));第一行第一个元素的大小
	printf("%d \n", sizeof(arr[3]));第四行元素的大小,(其实不存在)
				//但也能通过类型计算

区分一下sizeof 和 strlen的不同的作用

2.~

~ 对一个数的二进制按位取反

	int a = -1;
	int b = ~ a;
	printf("%d",b);		//结果为0

-1在内存的以补码的形式存储:11111111 11111111 11111111 11111111
按位取反后为:00000000 00000000 00000000 00000000
即可得到结果为0

(3)、(-- 、++)的应用

1.后置++(- -)

后置++(- -)先使用,后++(- -)

	int a = 5;
	int b = a++;
	printf("%d",b);// 5
	printf("%d",a);//6
2.前置++(- -)

前置++(- -)先++(- -),后使用

	int a = 5;
	int b = ++a;
	printf("%d",b);//6
	printf("%d",a);//6

(4)、(* 、&)的应用

  • &取地址
  • * 间接访问操作符(解引用操作符)
	int a = 5;
	printf("%p",&a); //获取变量a的地址---并打印出来
	int* pa = &a;	//pa用来存放变量a的地址----
					//pa就是一个指针变量--类型为int型
	*pa = 3;		//'*'解引用操作符-间接访问操作符
	printf("%d",a);	//此时的a的值就会变为3

6.关系操作符

  • > 大于
  • >= 大于等于
  • <小于
  • <= 小于等于
  • != 不等于 (用于测试"不相等")
  • == 用于测试"相等"

在编程的时候一定要分清楚 === 的区别

7.逻辑操作符

  • && 逻辑与
  • || 逻辑或

区分逻辑与按位与 区分逻辑或按位或

1 & 2--------->0
1 && 2------->1


1 | 2 ------------>3
1 || 2------------>1

	int a = 5;
	int b = 3;
	if(a && b)	//此时为1,为真,进入表达式。
	{
		//表达式;
	}
	
	int a = 5;
	int b = 0;
	if(a && b)	//此时为0,为假,不进入表达式。
	{
		//表达式;
	}
	int a = 5;
	int b = 0;
	if(a || b)	//此时为1,为真,进入表达式。
	{
		//表达式;
	}
	
	int a = 0;
	int b = 0;
	if(a || b)	//此时为0,为假,不进入表达式。
	{
		//表达式;
	}

接下来看一道题目

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

i = a++ && ++b && d++;
在计算的时候第一步已经为 0 && ++b && d++; ,已经判断为假,后面的就不需要再计算,即结尾a++一下。

如果改一下条件

	int i = 0,a = 1,b = 2,c = 3,d = 4;
	i = a++ || ++b || d++;
	printf("a = %d\nb = %d\nc = %d\nd = %d\n",a,b,c,d);
	//a = 2 b = 2 c = 3 d = 4

在计算的时候第一步已经为 1 || ++b || d++;,已经判断为真,后面的就不需要再计算,即结尾a++一下。

8.条件操作符

条件操作符也叫三目操作符

	int a = 5;
	int b = 3;
	if(a > 3)
	b = 1;
	else 
	b = -1; 
	// 等价于下面的代码
	int a = 5;
	int b = 3;
	b = (a > 3 ? 1:-1);

9.逗号表达式

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

接下来看两个例子

	int a = 3;
	int b = 5;
	int c = 0;
	int d = (c = 5,a = c + 3,b = a - 4,c += 5);
	printf("%d",c);   // 10
#include<stdio.h>
int main()
{
	int arr[] = {1,2,(3,4),5};
	// 数组元素中(3,4)其实就是逗号表达式
	//根据逗号表达式的原理可得 arr 中的元素为:{1,2,4,5}
	printf("%d",sizeof(arr));// 16
	return 0;
}

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

1. [ ]下标引用操作符

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

	int arr[10] = {0,1,2,3,4,5,6,7,8,9,10};
	printf("%d",arr[5]); // []---就是下标引用操作符
						 // 操作数 arr , 5
2.函数调用操作符

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

int add(int a,int b)
{
	return a + b;
}
int main()
{
	int a = 3;
	int b = 5;
	int ret = add(a,b);// ()-----括号就是函数操作数
					   // add--第一个参数,a,b------剩余的操作数
	return 0;
}
3.访问结构的成员
  • .结构体.成员名
  • ->结构体指针->成员名
	#include<stdio.h>
	struct book
	{
		char name[20];
		char id[20];
		int price;
	};
	int main()
	{
		int num = 10;
		struct book b = {"C++","C2022_06_18",13};
		// . -------操作符
		printf("%s\n",b.name);
		printf("%s\n",b.id);
		printf("%d\n",b.price);
		return 0;
	}

	#include<stdio.h>
	struct book
	{
		char name[20];
		char id[20];
		int price;
	};
	int main()
	{
		int num = 10;
		struct book b = {"C++","C2022_06_18",13};
		struct book* pb = &b;
		//  .--------->操作符   解引用指针访问成员变量
		printf("%s\n",(*pb).name);
		printf("%s\n",(*pb).id);
		printf("%d\n",(*pb).price);


		->-------操作符
		printf("%s\n",pb->name);
		printf("%s\n",pb->id);
		printf("%d\n",pb->price);
		return 0;
	}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值