桐庐城乡建设局网站,wordpress后台查看文章,百度一下你就知道移动官网,wordpress4.94主题上传不显示最近搞了许多有趣的东西#xff0c;比如自制rtos#xff0c;速成数模电#xff0c;学了一点点的AD#xff0c;看着视频弄了HAL库#xff0c;以及定时器和串口中断配合实现接收任意长度#xff08;不超过缓冲值#xff09;数据#xff0c;还有配置hal库的freertosfafts …最近搞了许多有趣的东西比如自制rtos速成数模电学了一点点的AD看着视频弄了HAL库以及定时器和串口中断配合实现接收任意长度不超过缓冲值数据还有配置hal库的freertosfafts 今天到货了前两天买的硬件十万个为什么又下单了H750VB板子这两天过敏又犯了 无语一字难受。
总结一下大二暑假学的东西
定时器判断长短按
定时器和串口判断一帧数据
bootloader
三极管mos管
防反接电路
dcdc电源原理ldo电容滤波原理
元器件的认识磁珠电感电容电阻各种二极管
esp8266获取天气
C语言结构体常用函数关键字指针等知识点总结。
手写i2c读rom学习spi读写flash和sd卡
做完辅助穿衣机器人的程序
嘉立创画完温湿度检测的板子
keil调试方法
hal库的使用
can
步进电机
一点点的AD
在此更新一些C语言杂乱知识点和疑难杂症........ 函数指针和指针函数 函数指针
本质是指针指向一个函数 。
qsort
void qsort (void* base, size_t num, size_t size,int (*compar)(const void*,const void*));// base - 需要排序的数组的起始地址
// num - 数组内元素的个数数组的大小
// size - 一个元素的大小单位是字节
// int (*compar)(const void*,const void*) - compar(一个函数指针)类型是 int (*)(const void*,const void*)
c - qsort函数使用方法总结详细全面代码 - 个人文章 - SegmentFault 思否https://segmentfault.com/a/1190000038746268指针函数和函数指针_指针函数 函数指针-CSDN博客https://blog.csdn.net/u010280075/article/details/88914424?ops_request_misc%257B%2522request%255Fid%2522%253A%2522172407382416800182122635%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257Drequest_id172407382416800182122635biz_id0utm_mediumdistribute.pc_search_result.none-task-blog-2~blog~top_positive~default-1-88914424-null-null.nonecaseutm_term%E5%87%BD%E6%95%B0%E6%8C%87%E9%92%88spm1018.2226.3001.4450C语言---qsort 函数详解与实现快速排序任何类型-CSDN博客https://blog.csdn.net/2302_78684687/article/details/137467421
大家也都能了解这个函数的重点就在于 compar 这一函数指针。
问题是怎么使用qsort来对一个数组进行排序 上面是对qsort四个参数的介绍其中数组起始地址就是数组名这点在上一篇文章中指针和数组的关系中讲过江科大的指针视频中也提到过。
后面是数组的元素个数和每个元素的大小
char shuzu[]{1,2,3,4,5,6,77,8}
//数组元素个数
sizeof(shuzu) / sizeof(char) ;
//每个元素的字节大小
sizeof(shuzu[0]);
sizeof(char) 和 sizeof(shuzu[0]) 是一样的。
最最重点的就是第四个参数是一个函数函数名可以自由定义但是参数必须和qsort给的如出一辙即为
char sum_int(const void* p1, const void* p2)
{
// return (int)(*(int*)p1 - *(int*)p2); //-升序return (int)(*(char *)p2 - *(char*)p1); //-降序
}
qsort函数根据函数指针所指向的函数的返回值和 0的关系做出判断从而进行排序所以至于是从大到小还是从小到达可以自己决定。
在 sum_int() 函数中需要将参数p1和p2转义为数组的定义类型。p1p2是指针数值等于地址 。所以char*的转义符前面还有一个*代表p1p2所指向地址的数值 。
最近看的回调函数也和函数指针相关。 指针函数
本质是函数返回一个指针 。返回指针的函数叫指针函数
#include stdio.h
#include stdlib.h
char *get_num ( char *n,const char *m);
int main()
{char a1[100] hello;char a2[] world;printf(%s, get_num(a1,a2));
}char *get_num ( char *n,const char *m)
{char *pn;while(*n ! \0) { n; }while(*m ! \0) { *n *m ;} *n \0;return p;
}
结果为helloworld
定义 函数 get_num实现字符串的拼接并返回拼接好的字符串的起始地址。
原来pritf函数打印字符串的时候输入字符串的地址就行比如 char a2[] world;printf(%s, a2);
a2 是数组名 也就是数组地址 。
在 函数 get_num 内部用循环将指针 n 指向到数组 n 的末尾 之后从数组 a 的末尾开始用循环取m的值一位一位的的赋值给n指导数组m结束实现字符串的拼接。 浮点数在内存中的存储 C语言---浮点数在内存中的存储_c浮点数存储-CSDN博客https://blog.csdn.net/2302_80826557/article/details/137436685?ops_request_misc%257B%2522request%255Fid%2522%253A%2522172407546616800172520370%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257Drequest_id172407546616800172520370biz_id0utm_mediumdistribute.pc_search_result.none-task-blog-2~blog~sobaiduend~default-1-137436685-null-null.nonecaseutm_term%E6%B5%AE%E7%82%B9%E6%95%B0%E5%9C%A8%E5%86%85%E5%AD%98%E4%B8%AD%E7%9A%84%E5%AD%98%E5%82%A8spm1018.2226.3001.4450在浮点数进行判断的时候在浮点数后边加一个f
如下图所示
int main()
{float f12.2;if(f1 2.2) printf(2.2 2.2\r\n);else printf(no xiangdeng\r\n);if(f1 2.2f) printf(2.2f 2.2f\r\n);else printf(no xiangdeng\r\n); } 可见对f1进行判断的时候加一个f才能输出正确的结果。 安规电容 安规电容在电路中用于过滤干扰信号X电容用于抑制差模干扰Y电容用于抑制共模干扰 。 数组与指针 对于以下代码猜猜在存储区一共存储了几个 hello
#include stdio.h
#include stdlib.hint main()
{char *s1hello;char *s2hello;char a1[]hello;char a2[]hello;printf(%p %p %p %p,s1,s2,a1,a2);}
其中 *s1 指向的 hello 是一个字符串常量在静态存储区静态存储区直到执行结束内存才被回收s1和s2指向的内容一样所以地址一样。
a1 和 a2是局部变量放在栈里可以随时修改所以a1和a2是两个不一样的hello总的来说看来是变量存储的位置不同从而带来的影响。
a1代表的是数组名也就是数组的地址是地址常量存储在静态存储区地址常量不能被修改。也就是说 a1;是错误的地址上面的数值可以修改比如 *a1[0] H;是对的。
s1是一个指针指针是可以变的指向的是hello的地址也可以变成其他字符串的地址。 所以 s1是合法的再次打印 *s1 得到的结果为 ello 字符串常量hello是不能被修改的比如
*s1[0] H 会报错。
其中指针和数组占用的内存也不一样。
数组占用的内存为字符个数乘以变量类型字节长度。
指针大小为系统位数除以8 。 二维数组 数据结构 | 二维数组的元素地址。【按行或按列存储】时行列对换坐标元素的起始地址保持不变-CSDN博客https://blog.csdn.net/weixin_52700125/article/details/134883240?ops_request_misc%257B%2522request%255Fid%2522%253A%2522172407755216800184153816%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257Drequest_id172407755216800184153816biz_id0utm_mediumdistribute.pc_search_result.none-task-blog-2~blog~sobaiduend~default-2-134883240-null-null.nonecaseutm_term%E4%BA%8C%E7%BB%B4%E6%95%B0%E7%BB%84%E5%85%83%E7%B4%A0%E7%9A%84%E5%9C%B0%E5%9D%80spm1018.2226.3001.4450
元素的地址等于起始地址加上元素在数组中排在元素前面的所有元素所占的内存大小。对于二维数组分为行和列。比如数组定义为a[2][4]那么a[1][1]前面的元素包括a[0][1]a[0][2]a[0][3]a[0][4] 。
二维数组如何进行传参
#include stdio.h
#include stdlib.h
int get_num(int n,int m,int (*p)[m]);
int main()
{
int a[3][3]{{1,4,7},{3,7,1},{9,4,2}};
int sum ;sum get_num(3,3,a);
printf(%d\n,sum);
return 0;}数组指针 int (*p)[m]
(*p)代表数组名[m]代表他每一行有m个列。int get_num (int n,int m,int (*p)[m])
{int sum 0;int i,j;for(i0;in;i){for(int j0;jm;j){sum p[i][j];printf(%d\r\n,*(*(pi)j)); //先找行再找列再取值} }return sum;
}
运行结果 指针常量和常量指针 常量指针本质是指针 指针指向的地址的内容不能被改变 可以更改指针指向的地址来改变指针对应的数值 指向常量的指针 。
指针常量本质是常量 指针指向的内容的地址不能被改变 可以更改指针指向的内容来改变指针对应的数值 指针本身是个常量 。
常量指针和指针常量的区别_指针常量和常量指针的区别-CSDN博客https://blog.csdn.net/weixin_46280821/article/details/126652869?ops_request_misc%257B%2522request%255Fid%2522%253A%2522172407987416800213061084%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257Drequest_id172407987416800213061084biz_id0utm_mediumdistribute.pc_search_result.none-task-blog-2~blog~top_positive~default-1-126652869-null-null.nonecaseutm_term%E5%B8%B8%E9%87%8F%E6%8C%87%E9%92%88%E5%92%8C%E6%8C%87%E9%92%88%E5%B8%B8%E9%87%8Fspm1018.2226.3001.4450 数组指针和指针数组 数组指针与指针数组的区别_数组指针和指针数组的区别-CSDN博客https://blog.csdn.net/super_demo/article/details/19679053?ops_request_misc%257B%2522request%255Fid%2522%253A%2522172408134016800222843329%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257Drequest_id172408134016800222843329biz_id0utm_mediumdistribute.pc_search_result.none-task-blog-2~blog~sobaiduend~default-2-19679053-null-null.nonecaseutm_term%E6%95%B0%E5%80%BC%E6%8C%87%E9%92%88%E5%92%8C%E6%8C%87%E9%92%88%E6%95%B0%E7%BB%84spm1018.2226.3001.4450数组指针 指向一个数组的指针
数组指针经常和二维数组连用。 链表 手撕链表
数据结构之手撕链表讲解➕源代码-CSDN博客https://blog.csdn.net/2302_76941579/article/details/133846023?ops_request_misc%257B%2522request%255Fid%2522%253A%25225ECE9487-2A28-4479-852E-93DC3E8A40C1%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257Drequest_id5ECE9487-2A28-4479-852E-93DC3E8A40C1biz_id0utm_mediumdistribute.pc_search_result.none-task-blog-2~all~sobaiduend~default-2-133846023-null-null.142^v100^pc_search_result_base9utm_term%E6%89%8B%E6%92%95%E9%93%BE%E8%A1%A8spm1018.2226.3001.4187
#include stdio.htypedef int datatype;//定义结构体
/*您提供的代码片段是一个C语言中的结构体定义使用了typedef关键字来
定义一个结构体类型listnode和一个指向该结构体的指针类型linklist。
这种定义方式在数据结构中常用特别是在处理链表时可以简化代码中的类型
声明。结构体listnode包含两个成员一个整型数据data和一个指向下一个
listnode结构体的指针next。通过typedef关键字listnode成为
了结构体类型的别名而linklist成为了指向该结构体的指针类型的别名。
这样在后续的代码中可以直接使用listnode和linklist来声明变量
而不需要每次都写出完整的结构体类型和指针类型。这种定义方式在C语言中是合法的并且是一种常见的编程技巧
用于提高代码的可读性和可维护性.*/typedef struct node{
int data;
struct node *next;
}listnode,*linklist;linklist list_create();//列表创建函数
int head_insert(linklist H,datatype data);//列表头部插入函数
int list_show(linklist H);//列表遍历打印函数int main(){linklist H;if ((H list_create()) NULL ){ return 0;} head_insert(H, 50);head_insert(H, 50);head_insert(H, 100);head_insert(H, 20);head_insert(H, 50);list_show(H);return 0;
}linklist list_create()
{linklist H;if((H (linklist)malloc(sizeof(listnode))) NULL){return H;} H-data 0;H-next NULL;return H;
}
//没有释放掉申请的内存需要注意
int head_insert(linklist H,datatype data)
{ linklist p;if(H NULL) {return -1;}if((p (linklist)malloc(sizeof(listnode))) NULL){ printf(malloc failed);return -1;}p-data data;p-next H -next;H-next p;return 0;
}int list_show(linklist H)
{if(H NULL || H -next NULL){return -1;}H H-next;while(H ! NULL){//最后一个链表节点的指针为NULLprintf(%d\r\n,H-data);H H-next;}printf(\n);return 0;
} 实验现象 对结构体指针指向的字符串进行修改的放法 指针与字符串-CSDN博客https://blog.csdn.net/qq_43680827/article/details/122929776?ops_request_misc%257B%2522request%255Fid%2522%253A%2522172416196116800182767696%2522%252C%2522scm%2522%253A%252220140713.130102334.pc%255Fall.%2522%257Drequest_id172416196116800182767696biz_id0utm_mediumdistribute.pc_search_result.none-task-blog-2~all~first_rank_ecpm_v1~rank_v31_ecpm-4-122929776-null-null.142%5Ev100%5Epc_search_result_base9utm_term%E5%AD%97%E7%AC%A6%E4%B8%B2%E5%92%8C%E6%8C%87%E9%92%88spm1018.2226.3001.4187直接对指针定义结构体指针指向的是存放在静态存储区的字符串的地址
对结构体指针指向的字符串直接进行修改失败的原因也是静态存储区的常量不能被修改
比如 s1.name[0] H ; 是错误的 。
自己申请一段堆上的空间
并不是实现对精彩存储区常量的修改而是实现了申请内存的方法修改结构体指针指向的存在堆区的字符串的内容。所以结构体指针指向的字符串还是不能直接定义需要用其他方法原因还是直接定义就是定义静态常量不能修改。
#include stdio.h
#include string.h
#include stdlib.h
#define N 50struct student{int num;char *name;
};int main(){
struct student s1 {1,guangtouqiang};
struct student s2;
s2.num 2;//s1.name[0] G;if((s2.name malloc(N*sizeof(char))) NULL) { return 0;}//s2.name xiongda;
strcpy(s2.name,xiongda);
s2.name[0] X;printf(%d %s\r\n,s1.num,s1.name);
printf(%d %s\r\n,s2.num,s2.name);free(s2.name);
s2.name NULL;
}