题目:
有一对兔子,从出生第3个月起每个月都生一对兔子,小兔子长到第3月后每个月又生一对兔子。假设所有兔子都不死,编程求第20个月总数为多少?
难点:从第3月起,能生小兔子的大兔子每个月都要生一对兔子。
分析:
单位(对)
月 份 | 小兔子 | 中兔子 | 大兔子 | 兔子总数 |
1 | 1 | 0 | 0 | 1 |
2 | 0 | 1 | 0 | 1 |
3 | 1 | 0 | 1 | 2 |
4 | 1 | 1 | 1 | 3 |
5 | 2 | 1 | 2 | 5 |
6 | 3 | 2 | 3 | 8 |
7 | 5 | 3 | 5 | 13 |
8 | 8 | 5 | 8 | 21 |
9 | 13 | 8 | 13 | 34 |
10 | 21 | 2 | 21 | 55 |
11 | 34 | 2 | 34 | 89 |
- 此时可找出规律:每个月总数是前两个月总数之和
方法一
从第三个月开始计算。前面两个月兔子数量确定(n1;n2),后面每个月的兔子数量等于前两个月兔子数量之和。前一个月的兔子数n2;前两个月的兔子数n1;所以从第三个月开始(n),兔子数量为n=n1+n2。此后前两个月的数目进行更新向后移动一月,方便下一个循环。
void main ()
{
int i,n,n1=1,n2=1;
for(i=3;i<=20;i++)
{
n=n1+n2;//本月兔子的数目(第三月开始)
n1=n2;//n1指向后移一位
n2=n;//n2指向后移一位
printf("第%2d个月兔子总数为%4d对\n",i,n);
}
printf("第20个月兔子总数为%d对",n);
}
方法二
从第一个月开始循环,将第一个月的数量先存储起来k=f1,在将后面两个月的兔子数量更新。后面第一个月的兔子数改变为后面第二个月f1=f2,后面第二个月的兔子数为前两个月之和f2=f2+k(f1未改变时的值)。
#include <stdio.h>
int main()
{
long f1=1,f2=1,k;
int i;
for(i=1;i<=20;i++ )
{
k=f1;//第i个月的兔子对数
f1=f2;//后面一个月的兔子对数
f2=k+f2;//后面二个月的兔子对数
printf("第%2d月有%4ld对兔子;\n", i,k);
}
}
方法三
每个循环处理两个月。每次更新,第一个月是前两个月之和f1+f2,第二个月也是前两个月之和f2=f2+f1(此时f1已经改变)
int main( )
{
long f1=1,f2=1;
int i;
//每次循环确定2个月的兔子个数
for(i=1;i<=10;i++)
{
printf("第%2d月有%4ld只兔子;\n第%2d月有%4ld只兔子;\n",2*i-1,f1,2*i,f2);
f1=f1+f2;//第2n-1个月兔子数
f2=f2+f1;//第2n个月兔子数
}
}
方法四
可以使用递归的方式求解大家可以自己试试。
- 规律:每个月总数是前两个月总数之和,满足斐波那契数列规律,可以直接按照求斐波那契数列的方法直接求解。需要注意最后的结果是兔子对数(一对2只)不是个数。