函数的递归调用
在调用一个函数的过程中又直接或间接地调用该函数本身、
(程序设计)用递归方法求n!。
#include<iostream>
using namespace std;
long fac(int);//函数声明
int main()
{
int n;
long y;//y为存放n!的变量
cout << "Please input an integer:" << endl;
cin >> n;
y = fac(n);
cout << "n!=" << y << endl;
return 0;
}
long fac(int n)
{
long f;
if (n < 0) {
cout << "Data error." << endl;
f = -1;//如果输入负数,报错并以-1作为返回值
}
else if (n == 0 || n == 1) f = 1;
else f = fac(n - 1) * n;
return f;
}
内置函数
什么是内置函数?什么情况下使用内置函数?
在编译时将所调用函数的代码直接嵌入到主调函数中,而不是将流程转出去。这种嵌入到主调函数中的函数称为内置函数。指定内置函数的方法很简单,只需在函数首行的左端加一个关键字inline即可。
只有规模较小而又被频繁调用的简单函数,才适合声明为inline函数。此时函数调用的时间开销可能相当于甚至超过于执行函数本身的时间,把它定义为内置函数,可大大减少程序运行时间。
函数的重载
什么是函数的重载?使用时需要注意什么?
C++允许用同一函数名定义多个函数,而这些函数的参数个数和参数类型可以不相同。这就是函数的重载。所谓“重载”,即“一物多用”。
重载函数的参数个数、参数类型或参数顺序三者必须至少有一种不同,函数返回值类型可相同1也可不同。
(程序设计)求3个数中最大的数(分别考虑整数、双精度数、长整数的情况),用函数重载方法。
#include <iostream>
using namespace std;
int main(void)
{
int max(int a, int b, int c);
double max(double a, double b, double c);
long max(long a, long b, long c);
int i1, i2, i3, i;
cin >> i1 >> i2 >> i3;
i = max(i1, i2, i3);
cout << "i_max=" << i << endl;
double d1, d2, d3, d;
cin >> d1 >> d2 >> d3;
d = max(d1, d2, d3);
cout << "d_max=" << d << endl;
long g1, g2, g3, g;
cin >> g1 >> g2 >> g3;
g = max(g1, g2, g3);
cout << "g_max=" << g << endl;
return 0;
}
int max(int a, int b, int c)
{
if (b > a) a = b;
if (c > a) a = c;
return a;
}
double max(double a, double b, double c)
{
if (b > a) a = b;
if (c > a) a = c;
return a;
}
long max(long a, long b, long c)
{
if (b > a) a = b;
if (c > a) a = c;
return a;
}
函数模板
函数模板是什么?适用于什么情况?
函数模板,实际上是建立一个通用函数,其函数类型和形参类型不具体指定,用一个虚拟的类型来代替。这个通用函数就称为函数模板。
函数模板只适用于函数体相同、哈数的参数个数相同而类型不同的情况。
(程序设计)求3个数中最大的数(分别考虑整数、双精度数、长整数的情况),用函数模板方法。
#include<iostream>
using namespace std;
template<typename T>
T max(T a, T b, T c)
{
if (b > a) a = b;
if (c > a) a = c;
return a;
}
int main()
{
int i1 = 185, i2 = -76, i3 = 567, i;
double d1 = 56.87, d2 = 90.23, d3 = -3214.78, d;
long g1 = 67854, g2 = -912456, g3 = 673456, g;
i = max(i1, i2, i3);
d = max(d1, d2, d3);
g = max(g1, g2, g3);
cout << "i_max=" <<i<< endl;
cout << "d_max=" <<d<< endl;
cout << "g_max=" <<g<< endl;
return 0;
}
有默认参数的函数
对于有默认参数的函数,什么时候给出默认值?
如果函数的定义在函数调用之前,则应在函数定义中给出默认值。如果函数的定义在函数调用之后,则在函数调用之前需要有函数声明,此时必须在函数声明中给出默认值,在函数定义时可以不给出默认值。
重载函数可以是有默认参数的函数吗?
不能。调用函数时如果少写一个参数,系统无法判定是利用重载函数还是利用默认参数的函数,出现二义性,系统无法执行。
求两个或3个正整数中的最大数,用带有默认参数的函数实现。
#include<iostream>
using namespace std;
int main()
{
int max(int a, int b, int c = 0);
int a, b, c;
cin >> a >> b >> c;
cout << "max(a,b,c)=" << max(a, b, c) << endl;
cout << "max(a,b)=" << max(a, b) << endl;
return 0;
}
int max(int a, int b, int c)
{
if (b > a)
a = b;
if (c > a)
a = c;
return a;
}
变量的存储方式
动态存储区和静态存储区分别存储什么?
全局变量全部存放在静态存储区中,在程序开始执行时给全局变量分配存储单元,程序执行完毕就释放这些空间。
在动态存储区中存放以下数据:
- 函数形式参数
- 函数中定义的变量
- 函数调用时的现场保护和返回地址等
存储类别是什么?有哪几种?
存储类别指的是数据在内存中存储方法。存储类别有四种:
- 自动的;
- 静态的;
- 寄存器的;
- 外部的。
静态局部变量什么情况下使用?
- 有时希望函数中的局部变量的值在函数地哦啊用结合结束后不下时而保留原值,即其占用的存储单元不释放,在下一次该函数调用时,该变量保留上一次函数调用结束时的值。这时就应该指定该局部变量为静态局部变量。(系统中的局部变量,如果不用关键字static声明,编译系统对它们是动态地分配存储空间的。)
- 如果初始化后,变量只被引用而不改变其值,则这时用静态局部变量比较方便,以免每次调用时重新赋值。
用static来声明一个变量的作用分别是什么?
- 对局部变量用static声明,使该变量在本函数调用结束后不释放,整个程序执行过程中始终存在,使其存储期为程序的全过程;
- 全局变量用static声明,则该变量的作用于只限于本文件模块(即被声明的文件中)。
头文件的内容
头文件一般包括哪些内容?
- 对类型的声明;
- 函数声明;
- 内置(inline)函数声明;
- 宏定义;
- 全局变量定义;
- 外部变量定义。如“entern int a”;
- 还可以根据需要包含其他头文件。
习题1:写一个判别素数的函数,在主函数中输入一个整数,输出是否为素数的信息。
#include <iostream>
using namespace std;
int main()
{
int prime(int);
int n;
cout << "input an integer:";
cin >> n;
if (prime(n))
cout << n << "is a prime." << endl;
else
cout << n << "is not a prime." << endl;
return 0;
}
int prime(int n)
{
int flag = 1, i;
for (i = 2; i < n / 2 && flag == 1; i++)
if (n % i == 0)
flag = 0;
return(flag);
}
习题2:求a!+b!+c!的值,用一个函数fac(n)求n!。a,b,c的值由主函数输入,最终得到的值在主函数输出。
#include <iostream>
using namespace std;
int main()
{
int fac(int);
int a, b, c, sum = 0;
cout << "enter a,b,c:";
cin >> a >> b >> c;
sum = sum + fac(a) + fac(b) + fac(c);
cout << a << "!+" << b << "!+" << c << "!=" << sum << endl;
return 0;
}
int fac(int n)
{
int f = 1;
for (int i = 1; i <= n; i++)
f = f * i;
return f;
}
习题3: 写一函数求sin(x)的值,求sin(x)的近似公式为sinh(x)=(ex-e(-x))/2。其中,用一个函数求e^x。
#include <iostream>
#include <cmath>
using namespace std;
int main()
{
double e(double);
double x, sinh;
cout << "enter x:";
cin >> x;
sinh = (e(x) - e(-x)) / 2;
cout << "sinh(" << x << ")=" << sinh << endl;
return 0;
}
double e(double x)
{
return exp(x);
}
习题4:写一个函数验证哥德巴赫猜想:一个不小于6的偶数可以表示为两个素数之和,如6=3+3,8=3+5,10=3+7,…,在主函数中输入一个不小于6的偶数n,然后调用函数gotbaha,在gotbaha函数中再调用prime函数,prime函数的作用是判别一个数是否为素数。在gotbah函数中输出以下形式的结果:
34=3+31
#include <iostream>
#include <cmath>
using namespace std;
int main()
{
void godbaha(int);
int n;
cout << "input n:";
cin >> n;
godbaha(n);
return 0;
}
void godbaha(int n)
{
int prime(int);
int a, b;
for (a = 3; a <= n / 2; a = a + 2)
{
if (prime(a))
{
b = n - a;
if (prime(b))
cout << n << "=" << a << "+" << b << endl;
}
}
}
int prime(int m)
{
int i, k = int(sqrt(m));
for (i = 2; i <= k; i++)
{
if (m % i == 0)
break;
}
if (i > k)
return 1;
else
return 0;
}
习题5:Hanoi(汉诺)塔问题。这是一个经典的数学问题:古代有一个梵塔,塔内有3个座A,B,C,开始时A座上有64个盘子,盘子大小不等,大的在下,小的在上(见图4.16)。有一个老和尚想把这64个盘子从A座移到C座,但每次只允许移动一个盘,且在移动过程中3个座上都始终保持大盘在下,小盘在上。在移动过程中可以利用B座,要求编程序打印移出移动的步骤。
#include <iostream>
using namespace std;
int main()
{
void hanoi(int n, char one, char two, char three);
int m;
cout << "input the number of diskes:";
cin >> m;
cout << "The steps of moving " << m << " disks:" << endl;
hanoi(m, 'A', 'B', 'C');
return 0;
}
void hanoi(int n, char one, char two, char three)
//将n个盘从one座借助two座,移到three座
{
void move(char x, char y);
if (n == 1)
move(one, three);
else
{
hanoi(n - 1, one, three, two);
move(one, three);
hanoi(n - 1, two, one, three);
}
}
void move(char x, char y)
{
cout << x << "-->" << y << endl;
}
习题6:用递归方法求f(x)=∑i^2(下标是i=1,上表是n)
n的值由主函数输入。
#include <iostream>
using namespace std;
int main()
{
int f(int);
int n, s;
cout << "input the number n:";
cin >> n;
s = f(n);
cout << "The result is " << s << endl;
return 0;
}
int f(int n)
{
if (n == 1)
return 1;
else
return (n * n + f(n - 1));
}
习题7:三角形的面积为 area=ss(s-a)(s-b)*(s-c)
其中,s=1/2(a+b+c),a,b,c为三角形的三边。定义两个带参数的宏,一个用来求s,另一个用来求area。编写程序,在程序中用带实参的宏名来求面积area。#include <iostream> #include <cmath> using namespace std; #define S(a,b,c) (a+b+c)/2 #define AREA(a,b,c) sqrt(S(a,b,c)*(S(a,b,c)-a)*(S(a,b,c)-b)*(S(a,b,c)-c)) int main() { float a, b, c; cout << "input a,b,c:"; cin >> a >> b >> c; if (a + b > c && a + c > b && b + c > a) cout << "area=" << AREA(a, b, c) << endl; else cout << "It is not a triangle!" << endl; return 0; }