西电期末1016.乘法口诀数列

一.题目

二.分析与思路

问题要先读懂,并不是a_{n}=a_{n-1}\times a_{n-2},这是错误的,更不是仅仅乘完之后取个位,而是如果大于十,将结果拆开,十位做下一项,个位做下两项,而且此时,计算的项不会因此也向后推动两项,仍然只会向后推一位。也就是说,计算是挨计算的,结果拆开直接加到数列末尾(不管加1个还是2个)。

那我们干脆也是这样,计算和结果的拼接分开来:首先定义i作为我们用来计算的位,记作计算位,由于我们要将结果加到末尾,就要有一个指向末尾的量,再定义一个偏移位j,使得i+j是最后一位。一开始i就是最后一位,我们初始化j=0,这样i+j就是最后一位,在计算出结果后,用i+j赋值,如果遇到计算结果是两位数,那么我们就要一次性加两个数,此时j++,使得i+j也会多加一位,就仍然是指向最后一位。

注意由于有可能一次循环加两项,所以最后出来的数列很有可能比原来多几项,但是无伤大雅,我们只需输出前n项即可。

最后注意,前两项先读入再放进数列的数组,因为数组长度在后面,只有先读入之后才能创建数组!

三.代码实现

#include<bits/stdc++.h>//万能头
int main()
{
    int a,b,n;
    scanf("%d%d%d",&a,&b,&n);
    int num[n];
    num[0]=a;num[1]=b;//初始化前两个
    int j=0;//推进位
    for(int i=2;i+j<n;i++){
        int t=num[i-1]*num[i-2];//计算位
        if(t<10){
            num[i+j]=t;
        }
        else if(num[i]>=0){
            num[j+i]=t/10;
            j++;
            num[j+i]=t%10;
        }//保证推进位+计算位等于当前数列长度
    }
    for(int i=0;i<n;i++){
        printf("%d ",num[i]);
    }
return 0;
}

四.评价

这道题已经有难度了,考察了程序员思维和非常规的读入,仔细研究!