嵌入式学习笔记十三——C语言指针变量、一维数组的指针、快速排序

news2024/9/21 22:38:41

指针变量

指针初始化

指针变量初始化:如果没有初始化,指针是随机值,既野指针。初始化可以让指针变量有明确的指向。

	int a = 10;
	int *p = &a;//指针初始化
	
	int *p = NULL; //NULL 0号地址   --- 空指针 

指针赋值

	int * p;
	p = NULL;
	
	int a;
	int *p;
	p = &a;
	
	int *p,q; //p是指针类型 int * 
	          //q是int型
    int *p,*q; //此时表示定义了两个 int*类型的变量 p 和q 
	           //注意:  
			   //定义时候的 * 修饰变量名的 表示定义的是一个指针类型的变量 

为什么需要地址?

    为了实现被调修改主调函数,值传递无法改变主函数中的数据,如果要对数据进行修改,就要用到指针进行地址传递。

指针作为函数的参数

形参:指针类型变量,用来接收实参,实参是要操作的内存空间的地址。

实参:需要修改的变量的地址,被调函数1中一定要有*运算

体会指针,被调修改主调,练习:1.找出两个数中最大值 和 最小值写成函数 2.写swap()函数,实现交换两数的值。     

#include <stdio.h>
void add(int n,int m,int *sum)
{
	*sum = n + m;
}
void findMaxMin(int n,int m,int *max,int *min)
{
	if(n>m)
	{
		*max = n;
		*min = m;
	}
	else 
	{
		*max = m;
		*min = n;
	}
}
void Swap(int *a,int *b)
{
	int t = *a;
	*a = *b;
	*b = t;
}
int main(void)
{
	int x=5,y=10;
	int sum;
	int max;
	int min;
//	add(x,y,&sum);
//	printf("%d\n",sum);
//	findMaxMin(x,y,&max,&min);
//  printf("max = %d\nmin = %d\n",max,min);
    Swap(&x,&y);
	printf("x = %d\ny = %d\n",x,y);
	return 0;
}

形参中的指针类型变量,只需定义需要修改的变量就可以,其他的值如果也用地址来操作就有些多于了,效率也会降低。需要修改的数据,在传入实参时要用取地址&来传入地址。

指针和一维整型数组

int  a[5]; 数组名a表示数组首元素的地址,数组名是个常量不能自增自减。

a =>&a[0]   a[0]的数据类型是int,&a[0]的数据类型是int*(指针类型)

int *p = a; p指向数组a

指针运算:&取地址,*指针运算(访问运算对象指向的地址)

p+1,p+n,p-1,p-n,p++,p--:表示(+向后,-向前)跳过了一个或n个基类型。

对数组指针进行自加减:

//打印数组
void printArray(int *a,int len)
{
	int i = 0;
	for (i = 0;i < len ;++i)
	{
		printf ("a[%d] = %d\n",i,*a++);
	//	printf ("a[%d] = %d\n",i,a[i]);
	//	printf ("a[%d] = %d\n",i,i[a]);
	//	printf ("a[%d] = %d\n",i,*(a+i));
	}
}

1. a <=>  &a[0]//a[0]的数据类型 -- int型 ,&a[0]  地址的类型 -- int* 

int *p = a; //表示 p指向数组a

此时*p等价于a[0],*p 访问指针p指向的地址中的内容。*p  <=> a[0]

2.*(p+i) <=> a[i] <=> *(a+i)//a是一个地址,代表首元素首地址,所以a = & a[0]  <=> p
 a[i]  <=> *(a+i)
 i[a]  <=> *(i+a) //a[i]==i[a];

所以上述代码中所有printf打印的内容都相同。

3.如果p,q,都是地址,则:

p - q     //表示差了多少元素(基类型)

两指针相减,必须是同一类型的指针  
          
p + q     是不允许的,会报错,没有意义。 

用指针可以实现用迭代的方式实现逆序,排序和查找。

练习:

1. 准备一个数组,找数组中的最大值 ,用指针完成。

2.数组逆序。

3.对数组排序。
 下面的代码只要修改主函数就能实现相关功能。

void findMax(int *a,int len)//找最大值
{
	int i = 0;
	 int max = *a;
	for (i = 0;i < len;++i)
	{
		if (*(a+i)>max)
			max = *(a+i);
	}
     return max;
}

void printArray2(int *begin,int *end)//打印
{
	while (begin <= end)
		printf("%d ",*begin++);
	putchar('\n');
}

void revArray(int *begin,int *end)//数组逆序
{
	int t;
	while(begin < end)//不用等于
	{
		t = *begin;
		*begin=*end;
		*end = t;
		++begin;
		--end;
	}
}
void selectSort(int *begin,int *end)//选择排序
{
	int *p;
	int *q;
	for (p = begin;p < end;++p)
	{
		for (q = p+1;q <= end;++q)
			if (*q < *p)
				Swap(q,p);
	}
}

void bubbleSort(int *begin,int *end)//冒泡排序
{
	int *p;
	int *q;
	for (p = end;p >begin;--p)
	{
		for (q = begin;q < p;++q)
		{
			if (*q > *(q+1))
				Swap(q,q+1);
		}
	}

}
void insertSort(int *begin,int *end)//插入排序
{
	int *p;
	int *q;
	for (p = begin+1;p <= end;++p)
	{
		int t = *p;
		q = p;
		while (q > begin && t < *(q-1))
		{
			*q = *(q -1);
			--q;
		}
		*q = t;
	}
}

int * binaryFind(int *begin,int *end,int n)//二分查找
{
	int *ret = NULL;
	int *mid;
	while (begin <= end)
	{
		mid = begin + (end - begin)/2;
		if(*mid < n)
			end = mid - 1;
		else if (*mid > n)
			begin = mid +1;
		else
		{
			ret = mid;
			break;
		}
	}
    return ret;

}

int main(void)
{
	int a[] = {1,5,7,8,4,1,3};
	int len = sizeof(a)/sizeof(a[0]);
//    printArray2(a,a+len-1);
    int max = 0;
	findMax(a,5,&max);
	printf("max = %d\n",max);
	insertSort(a,a+len-1);
//	revArray(a,a+len-1);
	int n;
	scanf("%d",&n);
	printArray2(a,a+len-1);
	return 0;
}


快速排序

思想:使用分治法的策略来把一个序列分为较小和较大的两个子序列,然后递归地排序两个子序列。快速排序的基本思想可以概括为以下几个步骤:

1.选择基准值:从数组中选择一个元素作为基准值(pivot),通常选择第一个元素、最后一个元素或中间元素。

2.分区操作:重新排列数组,使得所有比基准值小的元素都在基准值的左边,所有比基准值大的元素都在基准值的右边。这个称为分区(partitioning)的过程。

3.递归排序:递归地将上述步骤应用到基准值左边和右边的子数组上。

4.结束条件:当子数组的大小减少到1或0时,递归结束。

理解过程:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1994352.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【机器学习西瓜书学习笔记——特征选择与稀疏学习】

机器学习西瓜书学习笔记【第十一章】 第十一章 特征选择与稀疏学习11.1子集搜索与评价特征特征选择为什么要特征选择如何进行特征选择子集搜索子集评价 11.2过滤式选择Relief适用场景如何确定相关统计量 11.3包裹式选择优缺点 11.4嵌入式选择与L1正则化L1/L2正则化L1正则化问题…

【微信小程序开发】——奶茶点餐小程序的制作(一)

&#x1f468;‍&#x1f4bb;个人主页&#xff1a;开发者-曼亿点 &#x1f468;‍&#x1f4bb; hallo 欢迎 点赞&#x1f44d; 收藏⭐ 留言&#x1f4dd; 加关注✅! &#x1f468;‍&#x1f4bb; 本文由 曼亿点 原创 &#x1f468;‍&#x1f4bb; 收录于专栏&#xff1a…

Nginx+Tomcat负载均衡、动静分离群集(群集)

实验主机&#xff1a;101 102 103 101:nginx 102:tomcat1 103:tomcat2 先配置两个tomcat服务器 拉进去所需的安装包&#xff1b; 同步会话开始搭建&#xff1b; 安装编译环境&#xff1b; 解压并移动到方便管理的地方&#xff1b; 然后在root的家目录下创建一个目录及测试…

Google安装JSON-handle扩展

JSON-hande下载地址&#xff1a; JSON-Handle 官网 - 打开json格式文件的浏览编辑器 1. 重命名扩展文件(crx)后缀 为 zip。 2. 解压zip成文件夹&#xff0c;保存到指定目录。 3. Google浏览器地址栏输入 “chrome://extensions/”回车。然后开启 开发者模式。 4. 点击“加载…

疯狂Java讲义_08_泛型

文章目录 泛型的传参若函数里的参数使用基类接受所有的派生类&#xff0c;怎么做&#xff1f; 类型通配符的上限类型通配符的下限 泛型的传参 注意 若类 Base 是类 Derived 的基类&#xff08;父类&#xff09;&#xff0c;那么数组类型 Base[] 是 Derived[] 的基类&#xff0…

【编码解码神器】CyberChef v10.18.9

# 简介 CyberChef 是一个在线编码解码工具&#xff0c;包含了四百多种在线编解码工具&#xff0c;它提供了一种简单易用的方式来对数据进行各种加密、解密、编码和解码操作。你可以把它想象成一个多功能的”数字厨房”&#xff0c;在这里&#xff0c;你可以用各种”烹饪”方法…

无人机与自主系统

无人机&#xff08;Unmanned Aerial Vehicle, UAV&#xff09;和自主系统正在迅速改变许多行业&#xff0c;从农业到物流&#xff0c;再到军事领域。无人机作为一种能够自主或半自主飞行的飞行器&#xff0c;结合自主系统的技术&#xff0c;具备了更高的灵活性和执行复杂任务的…

牛羊肉巨头的数字化战略:凯宇星辉如何领先市场

凯宇星辉的创业成长史&#xff0c;给出了中国牛羊肉企业如何从散户走向集团化经营的路线图。 总部位于大连的凯宇星辉&#xff0c;在牛羊肉进口贸易领域白手起家&#xff0c;十余年时间&#xff0c;已形成以澳新、南美、北美等全球三大牛羊肉主产区为主渠道的全球直采网络布局…

【linux|001】Unix和Linux的关系 及 它们的发展历史

&#x1f341;博主简介&#xff1a; &#x1f3c5;云计算领域优质创作者 &#x1f3c5;2022年CSDN新星计划python赛道第一名 &#x1f3c5;2022年CSDN原力计划优质作者 ​ &#x1f3c5;阿里云ACE认证高级工程师 ​ &#x1f3c5;阿里云开发者社区专家博主 &#x1f48a;交流社…

巴黎奥运会上,墨水屏标签能怎么玩?

截至8月7日&#xff0c;中国代表团在2024巴黎奥运会上已经斩获了22金21银16铜&#xff0c;合计59枚奖牌&#xff0c;位居奖牌第二。在为奥运健儿欢呼喝彩的同时&#xff0c;我们也注意到巴黎奥运会在环保方面的创新&#xff0c;并探讨如何应用墨水屏标签这一智慧显示技术&#…

[转]通俗易懂的LLM(上篇)

前言 2022年年底OpenAI发布ChatGPT&#xff0c;将LLM&#xff08;Large Language Model&#xff09;带向了一个新的高度&#xff0c;而2023年OpenAI继续放出大招&#xff1a;更强大的GPT-4问世&#xff0c;瞬间引爆了整个互联网圈。在这个大模型时代&#xff0c;作为一名NLPer&…

什么是oled?

LED 是有机发光二极管&#xff08;Organic Light-Emitting Diode&#xff09;的缩写&#xff0c;是一种先进的显示技术。与传统的液晶显示技术&#xff08;LCD&#xff09;不同&#xff0c;OLED 显示器不需要背光模块&#xff0c;因为每个像素本身可以发光。 OLED 的基本原理和…

文档控件DevExpress Office File API v24.1 - 支持基于Unix系统的打印

DevExpress Office File API是一个专为C#, VB.NET 和 ASP.NET等开发人员提供的非可视化.NET库。有了这个库&#xff0c;不用安装Microsoft Office&#xff0c;就可以完全自动处理Excel、Word等文档。开发人员使用一个非常易于操作的API就可以生成XLS, XLSx, DOC, DOCx, RTF, CS…

Java实战二 添加lombok使用@Data,编写第一个接口-用户注册并使用postman测试

添加lombok依赖 使用Data注解&#xff0c;省略写getter和setter 创建返回结果Result类 创建三层结构UserController类UserService接口UserServiceImpl实现类UserMapper接口 UserController编写注册接口register UserService定义方法 UserServiceImpl实现方法 UserMapper中编写s…

一款免费、简单、快速的JS打印插件,web 打印组件,基于JavaScript开发,支持数据分组,快速分页批量预览,打印,转pdf,移动端,PC端

前言 在数字化办公时代&#xff0c;打印需求呈现多样化和复杂化的趋势。现有的打印软件往往存在cao作繁琐、兼容性差、功能单一等问题&#xff0c;难以满足现代企业高效、灵活的打印需求。 为了解决这些痛点&#xff0c;一款简单、高效、多功能的打印插件成为了迫切需求。 介…

《MySQL数据库》数据导入、导出、表处理—/—<4>

一、插入数据 1、可使用外部工具navicat导入数据的情况下 因为部分公司不允许使用外部工具去导入数据 对于大批量数据&#xff0c;除了上节课中使用导入向导插入数据&#xff0c;也可在vscode中打开csv文件&#xff0c;然后选中光标&#xff0c;长按shiftctrl&#xff0c;拖动…

基于springboot的小微企业融资征信平台系统的设计与实现-计算机毕业设计源码99083

摘 要 本文详细阐述了一个基于Spring Boot框架的小微企业融资征信平台系统的设计与实现过程。该系统旨在为小微企业、金融机构以及征信机构提供一个高效、安全的融资征信交流平台。系统支持企业用户的登录注册、首页浏览、交流论坛参与、通知公告查看、新闻资讯阅读以及个人账户…

点亮童梦思考之光,神秘伙伴震撼登场!

本文由 ChatMoney团队出品 介绍说明 咱们来聊聊“十万个为什么”机器人&#xff0c;这对小朋友来说&#xff0c;好处可多了去啦&#xff01; 小朋友们天生好奇&#xff0c;满脑子都是问号。 这个机器人就像个啥都懂的知识达人&#xff0c;不管他们问啥&#xff0c;都能给出答…

数据加密-AES数据加密WPF程序

AES&#xff08;Advanced Encryption Standard&#xff09;是一种广泛使用的对称密钥加密算法&#xff0c;由美国国家标准与技术研究院&#xff08;NIST&#xff09;于2001年发布。AES以其高效、安全的特点&#xff0c;在数据加密领域占据了重要地位。 <Grid><Grid.Ro…

定期检查m000是否消耗pga

偶然发现一个库的m000占用pga较高&#xff0c;导致ora-4036问题 sho parameter ga 看看当前参数 好像是bug 需要定期检查 select to_char(sysdate,yyyy-mm-dd hh24:mi:ss)riqi from dual;select round(sum(PGA_ALLOC_MEM)/1024/1024,2) "Total PGA Allocated (Mb)&q…