库函数
🔔 IO函数 input/output printf/scanf getchar/putchar … 🔔 字符串操作函数 strlen strcmp… 🔔 字符操作函数 🔔 内存操作函数 memcpy memset memmove 🔔 时间/日期函数 time 🔔 数学函数 sqrt
😰我们想把整型数组的前五个数用memset设置为1,这是没法实现的
int arr[10] = { 0 };
memset(arr, 1, 5*sizeof(int));
memset把每个字节设置为1,一个整型是4个字节,转换为十六进制就很容易看到,前20个字节都变成了1
自定义函数
🏸 函数的组成:
ret_type fun_name(para1, * )
{
statement;
}
ret_type 返回类型
fun_name 函数名
para1 函数参数
函数返回的表达式的值要和返回类型一致,返回类型要和接收这个函数的类型一致,如果不一致强制类型转换
? 写一个交换函数 一般会先想到这么写
void Swap(int x, int y)
{
int ret =x;
x = y;
y = ret;
}
但这是错误的,两个数并没有交换 调试去发现问题 可以发现swap里的x,y地址不和a,b一样,x,y交换,并不会改变a,b,空间上没有联系 ?????? 形参是实参的一份拷贝,形参的改变不会影响实参
我们可以通过解引用和取地址操作来解决
void Swap(int* pa,int* pb)
{
int ret = *pa;
*pa = *pb;
*pb = ret;
}
不调用函数,函数不会分配空间
printf 函数返回的是打印在屏幕上的字符的个数 如果发生错误,返回负数
printf("%d", printf("%d", printf("%d", 43)));
🥉函数必须先声明后定义,要想main函数后面定义函数,必须在main函数前声明
函数递归
函数调用自身的编程技巧叫做递归 通常把一个大问题层层转换为与原问题相似的规模较小的问题
递归的两个必要条件:1.存在限制条件,满足限制条件后,递归不再继续。 2.每次递归调用之后越来越接近这个条件 | 给定一个数,打印它的每一位,比如:输入1234,打印1 2 3 4 ![在这里插入图片描述](https://img-blog.csdnimg.cn/0d41c9d380994aad8bc81b0778e32ec5.png#pic_center)
void Print(int x)
{
if (x > 9)
{
Print(x / 10);
}
printf("%d ", x % 10);
}
int main()
{
int num = 1234;
Print(num);
return 0;
}
如果一个递归无限的走下去,它会出现栈溢出
🥇编写一个函数,不允许创建临时变量,求出字符串长度 首先我们会写出下面这样的代码,创建了count临时变量
int my_strlen(char* ps)
{
int count = 0;
while (*ps != '\0')
{
count++;
ps++;
}
return count;
}
int main()
{
char arr[10] = "abcdef";
int len = my_strlen(arr);
printf("%d", len);
return 0;
}
<font color=red size=3用递归解决
int my_strlen(char* ps)
{
if (*ps != '\0')
{
return my_strlen(ps + 1)+1;
}
return 0;
}
指针变量+1:指针+1就是指向下一个元素的地址,指针类型不同,跳过的字节数量也就不同
1 1 2 3 5 8 13 21 34 55 ......
当数字个数n>2时,前两个数字的和等于第三个数字 当数字个数n<=2时,前两个数字都为1
通过递归来实现
int fib(int n)
{
if (n <= 2)
{
return 1;
}
else
{
return fib(n - 1) + fib(n - 2);
}
}
但是当我们想求第40个斐波那契数时,第三个斐波那契数被重复计算了三千多万遍,效率太低了 ,所以不适合用递归 建议用循环
int fib(int n)
{
int a = 1;
int b = 1;
int c = 1;
while (n > 2)
{
c = a + b;
a = b;
b = c;
n--;
}
return c;
}
getchar 是函数,从键盘读取字符;而scanf什么类型的都可以读取 getchar 是读取字符 为什么返回类型是int?? 1.getchar 返回的是字符,实质上就是返回字符的ASCII码值 2.EOF — end of file 也就是 -1 👼getchar 和 scanf 读取信息的时候,会看缓冲区里有没有数据,没有数据才会从键盘读取,scanf读取数据的时候,读到空格就不再读了
把"abcdef"逆序
循环方法:
void my_reverse1(char* ps,int len)
{
char* left = ps;
char* right = ps + len -1;
while (left < right)
{
char tmp = *left;
*left = *right;
*right = tmp;
left++;
right--;
}
}
递归实现:
void my_reverse(char* str)
{
int len = strlen(str);
char tmp = str[0];
str[0] = str[len - 1];
str[len - 1] = '\0';
if (strlen(str+1) > 2)
{
my_reverse(str + 1);
}
str[len - 1] = str[0];
}
递归实现n的k次方
int Pow(int n, int k)
{
if (k > 0)
{
return n * Pow(n, k - 1);
}
else if (k == 0)
{
return 1.0;
}
else
{
return 1.0 / Pow(n, -k);
}
}
|