函数
我们知道C语言是面向过程的编程语言,函数是C语言中模块化编程的最小单位,学编程的都会知道,所以,没有什么难点,但是对于C的函数,里面还是有一些需我们注意的地方,下面正式开始学习。
先来看一个例子,由于它太熟悉了,所以就不从头开始学习了:
运行结果:
对于这个简单的程序,其中蓝色说明部分是我们需要注意的,对于函数,是需要提前声明的,有以下几点:
①如果将声明给去掉,则会给出警告:
②如果函数写在调用方之前,则可以省去声明,如下:
编译也是能通过的:
③ 函数的声明的形参可以省略形参名,只要形参数据类型既可:
编译也是能通过的:
下面以一个小例子来做为练习---------猜数游戏
下面先贴出简单的流程图:
具体实现:
#include <stdio.h> #include <stdlib.h>//提供rand()随机函数 #include <ctype.h>//提供isspace判断字符为空的函数 void guess(int number);//根据一个系统生成的数字进行猜测,功能核心 int next();//是否还要继续参与猜字游戏 int getnumber();//输到一个数字,需在1~100之间 int main(void) { do { int unknown = rand() % 100 + 1;//系统随机生成一个数字,供用户进行猜测 guess(unknown);//把所有的猜测的逻辑都封装成一个函数,体现了函数的意义,模块化 } while (next()); return 0; } void guess(int number) { int count = 0; do { int guess_number = getnumber(); if (guess_number > number) printf("Too high\n"); else if (guess_number < number) printf("Too low\n"); else { printf("Congratulation: you win!\n"); break; } } while (++count != 10); } int getnumber() { int n; while (1) { printf("Your guess: "); if (scanf("%d", &n) != 1 || n < 1 || n > 100) { //说明输入的数字是无效的,给出错误提示 printf("Wrong number,need a number 1 ~ 100\n"); while (getchar() != '\n')//这时需用户输入回车才能重新输入 ; } else break; } return n; } int next() { int c; printf("Next game? (y/n): "); while (isspace(c = getchar()))//如果输入的是空字符,则不断循环,直到不是空字符 ; if (c == 'y') return 1; return 0; }
运行结果:
注意看下面第二次运行的结果:
而我们生成随机数的是用库函数randon(),在计算机中,随机数都是伪随机数,达不到现实中的真正意义上的随机数,这是由于算法是确定性来决定的,它的随机数是依赖于种子,所以通过man来查看其帮助:
而如果要实现每次运行生成的随机数不一样,那我们可以把当前时间做为种子,这样生成的随机数就应该不是一样的了,如下:
#include <stdio.h> #include <stdlib.h>//提供rand()随机函数 #include <ctype.h>//提供isspace判断字符为空的函数 #include <time.h>//提供了time()获取当前时间的函数 void guess(int number);//根据一个系统生成的数字进行猜测,功能核心 int next();//是否还要继续参与猜字游戏 int getnumber();//输到一个数字,需在1~100之间 int main(void) { srand(time(NULL));//设置随时数的种子为当前时间,保证每次运行都不一样 do { int unknown = rand() % 100 + 1;//系统随机生成一个数字,供用户进行猜测 guess(unknown);//把所有的猜测的逻辑都封装成一个函数,体现了函数的意义,模块化 } while (next()); return 0; } void guess(int number) { int count = 0; do { int guess_number = getnumber(); if (guess_number > number) printf("Too high\n"); else if (guess_number < number) printf("Too low\n"); else { printf("Congratulation: you win!\n"); break; } } while (++count != 10); } int getnumber() { int n; while (1) { printf("Your guess: "); if (scanf("%d", &n) != 1 || n < 1 || n > 100) { //说明输入的数字是无效的,给出错误提示 printf("Wrong number,need a number 1 ~ 100\n"); while (getchar() != '\n')//这时需用户输入回车才能重新输入 ; } else break; } return n; } int next() { int c; printf("Next game? (y/n): "); while (isspace(c = getchar()))//如果输入的是空字符,则不断循环,直到不是空字符 ; if (c == 'y') return 1; return 0; }
运行结果:
函数递归
下面通过实例来应用函数递归
①利用递归求阶乘【这个比较简单】
#include <stdio.h> unsigned int factorial(unsigned int); int main(void) { printf("factorial(5)=%u\n", factorial(5)); return 0; } //递归求一个数的阶乘 unsigned int factorial(unsigned int number) { if ( number == 0) return 1; else return (number*factorial(number-1)); }
运行结果:
通常递归实现的都能将它改为循环来实现,但是反过来就不一定了,如下:
②判断一个字符串是否是回文
定义:称正读和反读都相同的字符序列为“回文”,如“abba”、“abccba”、12321、123321是“回文”,“abcde”和“ababab”则不是“回文”。
实现方式一:循环的方式来实现:
#include <stdio.h> #include <string.h> //判断一个字符串是否是回文 int palindrome(const char* str) { int first = 0; int last = strlen(str) - 1; while (first < last) { if (str[first] != str[last]) return 0; ++first; --last; } return 1; } int main(void) { if (palindrome("abcdcba")) printf("abcdcba is palindrome\n"); else printf("abcdcba is not palindrome\n"); if (palindrome("abcd")) printf("abcd is palindrome\n"); else printf("abcd is not palindrome\n"); return 0; }
实现方式二:递归的方式来实现:
#include <stdio.h> #include <string.h> //利用递归来判断一个字符串是否是回文 int palindrome_r(const char* str, int first, int last) { if (first >= last) return 1; if (str[first] != str[last]) return 0; return palindrome_r(str, first+1, last-1); } int palindrome(const char* str) { return palindrome_r(str, 0, strlen(str)-1); } int main(void) { if (palindrome("abcdcba")) printf("abcdcba is palindrome\n"); else printf("abcdcba is not palindrome\n"); if (palindrome("abcd")) printf("abcd is palindrome\n"); else printf("abcd is not palindrome\n"); return 0; }
运行结果:
好了,关于函数的先学到这。