函数定义、嵌套、声明、递归、非递归灵活运用,c语言基础知识总结(四)

函数

函数的设计尽量高内聚低耦合(自己设计自己的)尽量不关系别人

尽量少使用全局变量:全局变量可以改变的地方比较多,不安全


1. 分类

库函数

  • IO函数:input/output/printf/scanf/getchar/putchar/
  • 字符串操作函数:strlen/strcmp/strcpy/stract
  • 字符操作函数:tolower/toupper
  • 内存操作函数:memcpy/memset/memmove/memcmp
  • 时间/日期函数:time
  • 数学函数:sqrt/abs/fabs/pow
  • 其他库函数:根据网站Reference - C++ Reference (cplusplus.com)学习函数

getchar/putchar:读取/输出字符

  • 返回类型是int整型,因为返回的是字母,字母对应ascii码值为整型数字

  • 读取失败时候会返回EOF —— end of file = -1

  • gets直接读一行不管有无空格

int main()
{
    int a = getchar();
}
//像scanf/getchar的函数 输入一段字符再回车,下一个此类函数会直接拿走剩下在缓冲区的'\n'
//scanf碰到空格就不会再读了相当于读了个'\0'
int main()
{
	char password[20] = {0};

	printf("请输入密码:>");
	scanf("%s", password);

	//把缓冲区中的内容
	int tmp = 0;//把空格之后的字符串存起来
	while ((tmp = getchar()) != '\n')
    {
		;//这里指什么都不做
	}

	printf("请确认密码(Y/N):>");
	int ch = getchar();
	if (ch == 'Y')
	{
		printf("确认成功\n");
	}
	else
	{
		printf("确认失败\n");
	}

自定义函数

无返回值/空函数 (以交换值函数为例操作)

void swap(int *x,int *y)//注意这里定义形参的类型是指针
{
	int z = 0;
	z = *x;
	*x = *y;
	*y = z;
}

int main()
{
	int a = 0;
	int b = 0;

	scanf("%d%d", &a, &b);
	swap(&a, &b);//注意这里是取的是a和b的地址
    //传参方式:传址调用

	return 0;
}

有返回值(例子相同作对比)

int swap(int x,int y)//注意这里定义形参的类型是整型
{
	int z = 0;
	z = x;
	x = y;
	y = z;
}

int main()
{
	int a = 0;
	int b = 0;

	scanf("%d%d", &a, &b);
	swap(a, b);//注意这里是取的是a和b的值
    //传参方式:传参调用

	return 0;
}

2. 函数的调用

传参调用:函数的形参和实参分别占有不同内存块,对形参的修改不会影响实参。

传址调用:可以使函数和函数外边的变量建立起联系,函数内部可以直接操作函数外部的变量。


3. 函数的嵌套使用

函数可以嵌套调用,但是不能嵌套定义。


4. 函数的链式访问

#include <stdio.h>
#include <string.h>
int main()
{
    printf("%d\n,strlen("abc"));//链式访问
    printf("%d", printf("%d", printf("%d", 43)));
    //printf的返回值是打印字符个数,所以输出结果为4321
    return 0;
}


5. 函数的声明

先声明后使用

int function1()
{
    
}
int function2(int a);
int main()
{
    function1();//函数在前面 就不用声明
    int function2(int a);//只要在使用之前声明就行
    function2();//函数在后面需要调用
}
int function2(int a)
{
    
}

在工程中函数的声明使用

  • 新建.c源文件,存放定义的函数
  • 新建.h头文件,存放函数的使用声明
  • 在需要使用该函数的文件中前头加上 #include “xx.h” 即可使用该函数

分块写代码好处:

  1. 多人协作(比如写一个计算机中,分 总模块 加法 减法 乘法 除法 分别分给不同的人去写)
  2. 封装和隐藏(购买外包代码)

​ 关于如何包装:将定义函数的.c文件和声明该函数的.h文件复制到新的项目中,将项目属性中,常规-配置类型-改成静态库.lib,然后运行。得到.lib文件,将.lib文件和.h文件放到所要应用的工程里,使用时候前加上

#include “xxx.h” 头文件 + #pragma comment(lib,“xxx.lib”) //导入静态库

ps: 可以在头文件中包含以下代码,无论在源文件声明多少次都只会拷贝一份

//关于一个test.h
#pragma once
extern xx;
//或者是
#ifndef __TEST_H__ //判断有没有声明
#define __TEST_H__
int num(int x);//函数的声明

#endif
//二者等价

6. 函数递归

  • 存在限制条件,当满足这个限制条件的时候,递归便不再继续。

  • 每次递归调用之后越来越接近这个限制条件。

Stack overflow 出现该错误 表示栈溢出 意味着限制条件没有限制住


7. 函数的递归和迭代

  • 在使用 fb(n)=fb(n-1) +fb(n-2)这个函数的时候如果我们要计算第50个斐波那契数字的时候特别耗费时

什么时候用递归:
1.当解决一个问题递归和非递归都可以使用,且没有明显问题。那就可以使用递归。
2.当解决一个问题递归写起来很简答,非递归比较复杂,且递归没有明显问题,那就用递归。.
3.如果说用递归解决问题,写起来简单,但是有明显问题,那就不能使用递归,得写出非递归的方式来解决。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

凛音Rinne

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值