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++知识库 -> LinuxC应用开发学习笔记(三) -> 正文阅读

[C++知识库]LinuxC应用开发学习笔记(三)

函数

1、函数的定义

数据类型 函数名 (【数据类型 变量名 】)

int i; 
	在main函数中,argc表示传递多少个参数,argv 表示传递的列表 ,字符指针数组的首地址 
	printf("hello!\n");//一个 进程的返回状态是给他的父进程看的, 
	printf("argc = %d!",argc);
	for(i=0;i<=argc;i++)
	{
		puts(argv[i]);
	}
	return 0;//结束当前函数 

2、函数的传参

值传递:不会改变互换的参数
地址传递

void swap(int *p,int *q)
{
	int tmp;
	tmp = *p;
	*p = *q;
	*q = tmp;	
}

全局变量传参

3、函数的调用

函数的嵌套调用
递归:一个函数直接或者间接的调用自身

4、函数与数组

函数和一维数组

/*
*int *p = a;
*->a    *a 	a[0]  &a[3] 	 p[i] 	p 		*p		p+1
*
*
*->int* 	int 	int   int*	 int 	int*	     int 	int*
*
*/

打印数组的数据
p[]等价一个指针 ,本质还是一个指针,形参。

void print_arr(int p[],int n); 

传递只是传递的一维数组的起始地址,因此要用指针偏移打印。

void print_arr(int *p,int n) 
{

	for(int i=0;i<=n;i++)
	{
		printf("%d",*(p+i));
	printf("\n");
	} 	
} 

交换指针数组的顺序

void func(int *p,int n)
{
	int i = 0,m;
	m = (n-1)/2;
	for(;i <= m;i++)
	{
		int temp,j;
		j = n-1-i;
		temp = p[i];
		p[i] = p[j];
		p[j] = temp;		
	}		
}

int a[] = {1,3,5,7,9};
	for(int i=0;i<sizeof(a)/sizeof(*a);i++)
	{
		printf("%d ",a[i]);
	}
	func(a,sizeof(a)/sizeof(*a));
	for(int i=0;i<sizeof(a)/sizeof(*a);i++)
	{
		printf("%d ",a[i]);
	}

函数和二维数组

/*
*int a[M][N] = {};	
*int *p = *a;
*int (*q)[N] = a;
*
*-> a[i][j]		*(a+i)+j			    a[i]+j			p[i]		*p
*-> q[i][j]		*q = *(q+0)			q			    p+3		q+2 
*
*->	int 		 int *				int *				int 		int 
*->	int 		 int *				int(*)[]			int *		int(*)[]
*/

打印二维数组

void print_double_arr(int *p,int n)
{
	for(int i=0;i<n;i++)
	{
		printf("%4d ",p[i]);
	}
	printf("\n");
	
} 
float average_score(int *p,int n)
{
	float sum = 0;
	for(int i=0;i<n;i++)
	{
		sum += p[i];
	}
	return sum/n;	
}
#define M 2
#define N 5
//第一种表示方式 
void print_double_arr1(int (*p)[N],int m,int n);
//第二种表示方式 
void print_double_arr1(int p[][N],int m,int n)
 {
	for(int i=0;i<m;i++)
	{
		for(int j=0;j<n;j++)
		{
//第一种打印方式 
			printf("%4d ",*(*(p+i)+j));
 //第二种打印方式 
			printf("%4d ",p[i][j]);
			printf("\n");
		}
	}	
} 

float average_score(int *p,int n)
{
	float sum = 0;
	for(int i=0;i<n;i++)
	{
		sum += p[i];
	}
	return sum/n;	
}

打印固定的行的元素,注意什么时候传递行指针,什么时候传递列指针

void find_num(int (*p)[N],int num)
{
	for(int i=0;i<N;i++)
	{
		printf("%4d",*(*(p+num)+i));	
	}
	printf("\n");
}

第一种表示方式 ,将二维数组转换成为一维数组 p等价于(p+0)

void print_double_arr(int *p,int n) {
	for(int i=0;i<n;i++)
	{
		printf("%4d ",p[i]);//第一种打印方式 
	}
	printf("\n");
} 
#define M 2
#define N 5
//void print_double_arr1(int (*p)[N],int m,int n);//第一种表示方式 
void print_double_arr1(int p[][N],int m,int n)  //第二种表示方式
{
	for(int i=0;i<m;i++)
	{
		for(int j=0;j<n;j++)
		{
		//	printf("%4d ",*(*(p+i)+j)); //第二种打印方式,以指针来遍历
			printf("%4d ",p[i][j]); //第二种打印方式,以下标来遍历
		}
	}	
}

函数与字符数组

char* mystrcpy(char *dest,const char *src)
{
	char *ret = dest;
	if((dest != NULL && src != NULL))
	{
//使用循环实现把数值实现拷贝
		while((*dest++ = *src++) != '\0')
		{
		}
	}	
	return ret;	
} 

定义一个字符指针函数,返回值是char*类型

har* mystrncpy(char *dest,const char *src,size_t n)
{
	int i;
	for(i = 0;i<n&&(dest[i] = src[i]);i++);
	dest[i] = '\0';//字符串结尾补上尾0
	return dest;
} 
char str1[] = "helloworld";
	char str2[128];
	mystrncpy(str2,str1,5); 
	puts(str2); 
	mystrcpy(str2,str1); 
	puts(str2); 

5、函数与指针

指针函数
返回值 *函数名 (形参)
如:int * fun(int);
指针函数:返回的是一个指针

int * find_num1(int (*p)[N],int num)
{
	if(num > M-1)
	{
		return NULL;
	}
	return *(p + num);
} 

指针函数:返回的是一个指针,指针所指向的是一个入口地址

int a[2][5] = {1,3,5,7,9,2,4,6,8,10};
	int num = 1;
	int *res;
	res = find_num1(a,num);
	if(res != NULL)
	{
		for(int i=0;i<N;i++)
		{
			printf("%4d ",res[i]);
		}
	}
	else
	{
		printf("can not find\n");
		
	} 

函数指针

类型 (*指针名)(形参);
如:int (*p)(int);
函数指针:函数名只是一段代码关联的入口地址

int add(int a,int b)
{
	return a + b;	
} 

int sub(int a,int b)
{
	return a - b;	
} 

int a = 3,b = 5;
int ret;
	//指向函数的指针,与指向函数的类型相匹配,函数名仅仅是一个入口地址。 
	int (*p)(int,int);
	int (*q)(int,int);	
	p = add;
	q = sub;
	ret = p(a,b);
	printf("%4d ",ret);
	ret = q(a,b);
	printf("%4d ",ret);

函数指针数组
类型 (*数组名 【下标】)(形参)
如:int(*arrN);//数组,数组中有N个元素,这N个元素都是指向函数的指针
int (*funcp[2])(int ,int );
函数指针数组:数组,每一项都是指针,指向函数

int a = 3,b = 5;
	int ret;
	int (*funcp[2])(int ,int); 
	funcp[0] = add;
	funcp[1] = sub;
	for(int i = 0;i<2;i++)
	{
		ret = funcp[i](a,b);
		printf("%d\n",ret);
	}

八、构造类型

1、结构体

(1)产生的原因和意义
存放多种不同类型变量。
(2)类型的描述
struct 结构体名字
{
数据类型 成员1;//结构体的类型名字是不占用存储空间的,因此不能直接初始化。
数据类型 成员2;

};//分号一定不能丢。
(3)嵌套定义

struct simp_st
{
	int i;
	char ch;
	float f;
	
};
struct birthday_st
{
	int year;
	int month;
	int day;	
};
struct student_st
{
	int id;
	char name[NAMESIZE];
	struct birthday_st birth;
	int math;
	int chinese;	
};

(4)定义变量(变量、数组、指针),初始化以及成员引用
成员引用:变量名.成员名
指针->成员名
(*指针).成员名
结构体的初始化

struct simp_st a = {123,456.789,'a'};
	printf("%d %f %c\n",a.i,a.f,a.ch);
	struct student_st stu = {10011,"Alal",{2011,11,11},98,97};

结构体的指针传参:

struct student_st *p = &stu;//占用一个指针大小
struct student_st arr[2] ={{10011,"Alal",{2011,11,11},98,97},{10012,"Jlal",{2012,12,12},91,92}};
	p = &arr[0]; 
//	struct student_st stu = {.math = 94,.chinese = 95};
	printf("%d %s %d-%d-%d %d %d\n",stu.id,stu.name,stu.birth.year,stu.birth.month,stu.birth.day,stu.math,stu.chinese);
	for(int i=0;i<2;i++,p++)  //p = p+1 跳跃一个指针的大小 
	{
		printf("%d %s %d-%d-%d %d %d \n",p->id,p->name,p->birth.year,p->birth.month,p->birth.day,p->math,p->chinese);
	}

(5)占用的字节大小
根据是否会字节对齐,如果字节对齐,那么占用字节数为对齐字节之后的大小,否则,是各个变量的大小的总和。比如:

struct simp_st
{
	int i;
	char ch;
//char ch1;//占用 12字节
	float f;
	//char ch2;//占用16字节
};字节对齐占用 12个字节,不对齐占用9个字节

(6)函数传参(值,地址)
值传递:耗费地址空间
地址传递:把变量的指针传过去,消耗的是一个指针的开销。
//传参的对内存而言开销非常大,可以选择使用指针传参。

void func(struct simp_st *b){
	printf("%d \n",sizeof(b));	
}
	struct simp_st a;
	struct simp_st *p = &a;
	printf("sizeof(p) = %d \n",sizeof(p)); 
	printf("sizeof(struct) = %d \n",sizeof(a)); //结构体对齐  address%sizeof 
	func(p);

2、共用体

(1)产生的原因和意义
多个成员共同存在,共用同一块内存空间根据所占内存最大的分配,只有一个成员是有效的。
(2)类型描述
union 共用体名
{
数据类型 成员名1;
数据类型 成员名2;

};
(3)嵌套定义

struct
{
	int i;
	char ch;
	union 
	{
		int a;
		char c;
	}un;
	float f;
};

union 
{	
	int a;
	double d;
	struct 
	{
		int arr[10];
		float f;
	}un;
	float f;
};

(4)定义变量(变量、数组、指针),初始化以及成员引用
成员引用:变量名.成员名
指针->成员名
(*指针).成员名
(5)占用内存大小
共用同一块内存空间根据所占内存最大的分配。
结构体和共用体嵌套得到32位的低16位和高16位的和 :巧妙

union  //定义形式
{
	struct 
	{
		uint16_t i;
		uint16_t j;
	}x;
	uint32_t y; 
}a;//定义形式
	a.y = 0x11223344;
	printf("%x \n",a.x.i+a.x.j);

(6)函数传参(值传递、地址传递)
地址传参节约开销。
(7)位域

union 
{
	struct
	{
		char a:1;    //a = 0 1
		char b:2;	   //b = 00 01 10 11
		char c:3;	   //c = 0 1
	}x;
	int y;
}x;

3、枚举类型

enum 标识符
{
成员1:;
成员2:;
...
}enum //宏定义预处理之后会被替换掉,而枚举类型在预处理之后不会被宏替换掉,就是很多的宏的集合 
{
	STA_RUNNING = 1,
	STA_CANCELED,
	STA_OVER	
}; 
	enum day a = SAT;
	printf("%d\n",a);
	struct job_st job1;
	/*获取任务状态*/
	switch (job1.state) 
	{
	case STA_RUNNING:
		//TODO
		break;
	case STA_CANCELED:
		//TODO
		break;
	case STA_OVER:
		//TODO
		break;
	default:
		//TODO
		break;
	}

九、动态内存管理
auto的分配都是在栈上的,malloc可以在堆上分配。
malloc 和free最好同一个函数,或者同一个模块当中
原则:谁申请,谁释放。
malloc
calloc //连续申请N块size内存的空间
realloc //重新为我分配一块内存空间,原来的空间往下继续扩展
free

int *p = NULL;
	p = (int *)malloc(sizeof(int)); 
	if(p == NULL)
	{
		
		printf("malloc() error!\n");
		return 0;
	}
	*p = 10;
	printf("%d \n",*p);
	free(p);
  C++知识库 最新文章
【C++】友元、嵌套类、异常、RTTI、类型转换
通讯录的思路与实现(C语言)
C++PrimerPlus 第七章 函数-C++的编程模块(
Problem C: 算法9-9~9-12:平衡二叉树的基本
MSVC C++ UTF-8编程
C++进阶 多态原理
简单string类c++实现
我的年度总结
【C语言】以深厚地基筑伟岸高楼-基础篇(六
c语言常见错误合集
上一篇文章      下一篇文章      查看所有文章
加:2021-11-27 09:43:57  更:2021-11-27 09:44:54 
 
开发: 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 9:28:19-

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