前言:
如今各位老铁们对“用c语言计算存款利息”都比较讲究,各位老铁们都想要分析一些“用c语言计算存款利息”的相关知识。那么小编在网络上汇集了一些有关“用c语言计算存款利息””的相关知识,希望大家能喜欢,你们快快来了解一下吧!今天这道题目是从开始做基础编程到现在为止,我自己认为除了“龟兔赛跑”之外的最难的一道题,因为它涉及到的数学关系比较复杂,比较繁琐,要考虑到的情况也比较多,我在做这道题目的时候遇到了许多问题,也踩了不少坑,我会与大家一起分享,避免再出现我一样的错误。
我们先来看看这道题目的要求。
题目要求
输入一个整数(位数不超过9位)代表一个人民币值(单位为元),请换成财务要求的大写中文格式,这里呢为了简便,就用小写的英文字母a到j来代表数字0到9,用大写的字母“Y、W、Q、B、S”来分别代表亿、万、千、百和拾几个大写的中文格式要求。
比方说23108,就是cWdQbBai,还有一个要求,那就是在打印输出的时候,零的用法需要符合中文的习惯。
梳理逻辑
乍一看,这道题目似乎并不难,但其实啊,最难的关键就在于如何让零的打印来符合我们中文的习惯,我这里简单地举个例子,因为要求整数地位数不超过9位,所以我们只需要考虑9位及以下位数的整数。
1、用小写字母a-j顺序代表大写数字0-9,这一部分较为简单,我们先来讨论一下,这与我们PAT乙级当中的第二题输出对应拼音有点相似,就是用一个数组来存储小写字母a-j,然后用对应的数字去对应相应的字母,再打印出相应的结果。
以题目给的813227345为例,我们是不是先需要分别得到各个数字。
那就是要用813227345去除以10取余数得到5,然后再除以10取整数得到81322734,之后再以此类推,把各个数字给提取出来,然后再与一个数组取进行对应。
所以,需要定义一个标记,也就是用到计数法,用一个count,然后放入到while循环当中去,所以我这里使用了count,主要是用于第二部分的代码。
char *zimu[10] = {"a","b","c","d","e","f","g","h","i","j"};//对应的字母部分int store[10];//用到一个数组来存储各个数字int count = 0;//代表在字母数组当中的位置int n = 0;//要用于输入的整数scanf("%d",&n);//输入的一个非负正整数 while(n!=0){ store[count] = n%10; n = n/10; count++; }
2、当解决完小写字母对应的问题后,接下来要解决的,就是位置对应的问题。
我们来仔细思考一下,每次提取出一个数字后,它是不是在数组中有它对应的位置。
初始的位置是0,那么之后的位置就是1,以此类推就是2、3、4、5、6、7、8、9。
当然也要用到一个数组来存储位置。
char *weizhi[9] = {"","S","B","Q","W","S","B","Q","Y"};//位置
之后就是打印了,在针对这边打印的时候,就是要特别注意一下,在数组中的数字是不同的,一个对应的是数字,另一个对应的是数组的下标。
这里之所以要写一个while循环,目的就在于逆序输出,我没有使用for循环,但我在网上查找了相关资料后,发现用for循环也能实现,这里呢,如果观众老爷们有什么更好的建议,欢迎在评论区留言,大家一起来探讨。
while(count>0){ count--; printf("%s", zimu[store[count]]); printf("%s", weizhi[count]); }
3、当前面这两步解决之后,我们已经能够拿到大部分的分数了,不过这里还要对输入的整数n等于0的时候,和小于0的时候进行一个单独讨论。
等于0的时候,那么只需要打印输出一个a即可,如果是小于0的话,那么就要重新输入。
提交到PAT平台,我们可以发现,此时我们已经拿到了一半的分数了。
所以,当遇到一道难题时,我们一定是可以找到简单的部分并且先完成的,至少我们能保证该拿的分数都能拿到。
最难的部分就在于其它三个关键点。
分别为:a.sample2不超过万,末尾多0
b.不超过亿,中间连续多0
c.正常中间存在0
这就是最为困难的地方了,也是为了满足出现零的时候,能符合中文的习惯。
那么,针对这个难点,我们就以实际例子作为一个参考。
比方说80000000,那么我们的讲法就是8亿,期望得到的结果应该是iY,而这与题目最初的说法,用小写字母a来代表0是有出入的。
换而言之,如果末端都是重复的零的话,会把末端的零都给抹去,也就是不会打印输出a。
那如果是中间有连续的零呢, 比方说800000008,那这个就是八亿零八元,期望得到的结果应该是iYai,而不是iYaWa...i。
这里呢,为了帮助大家能够更加清晰地理解,我把所有情况都给罗列出来了。
我在图中标红的,就是几个关键点,这几个关键点就是特别需要讨论的。
首先是末端为0的时候,注意,在万位为0的时候,我们要在结尾再多加一个字母“W”。
万位为0的时候,对应的位置是4,因为是倒序,所以位置越大,对应的越靠前,我们可以通过实例观察得到,从第4位到第6位的时候,也就是888800000、888000000、880000000这三种情况,我们是要额外加上一个W的,所以需要进行一个条件语句判断。
if(count>=4&&count<7){//举例888800000到880000000 printf("W"); }
接下来就是最最最困难的部分了,也就是在末端重复的零如何不显示字母“a”。
和在中间位置重复的零,只显示一个小写字母“a”。
这里呢,就需要另一个变量了,也就是当前位置的之前位置,或者说之后位置也可以,不过我这里为了更好理解,还是用了之前的位置作为一个变量。
就是比较之前位置的数和之后位置的数是否都等于0。
从当前位置往前面去找,前面的位置当然要满足大于等于0,然后进行判断,如果前面位置的数字不是0,那么就只是当前的count为0,所以就只要打印出一个a即可,反之,就继续进行循环查找。
frontcount = count-1;//count前面一个位置 while(frontcount>=0){ if(store[frontcount] != 0){//判断前面位置的数字是否等于0 printf("a"); count = frontcount; break; } frontcount--; }
而至于末端都是0的情况,也包含在这里面了,因为末端的0,也就是count=0的时候,我们的frontcount=-1,然后这里呢再进行一个额外的判断,就是frontcount=-1的时候,就直接返回即可。
if(frontcount==-1){//末端都为0的状态 return 0; }
可以发现,到这一步为止呢,我们的逻辑也梳理明白了,接下来就是把具体的代码实现给放上来。
代码实现
//币值转换#include <stdio.h>#include <string.h>int main() { char *zimu[10] = {"a","b","c","d","e","f","g","h","i","j"};//小写字母 char *weizhi[9] = {"","S","B","Q","W","S","B","Q","Y"};//位置 int store[10]; int n = 0; int count = 0;//用到一个计数法 int frontcount = 0;//要与下一个 scanf("%d",&n);//输入的一个非负正整数 if(n<0){ scanf("%d",&n); } if(n==0){//对n要进行一个单独判断 printf("a"); } while(n!=0){ store[count] = n%10; n = n/10; count++; } //那么,接下来就是要处理0的情况了 while(count>0){ count--; if(store[count]==0){ if(count>=4&&count<7){//举例888800000到880000000 printf("W"); } frontcount = count-1;//count前面一个位置 while(frontcount>=0){ if(store[frontcount] != 0){//判断前面位置的数字是否等于0 printf("a"); count = frontcount; break; } frontcount--; } if(frontcount==-1){//末端都为0的状态 return 0; } } printf("%s", zimu[store[count]]);//打印0-9对应的字母 printf("%s", weizhi[count]);//打印亿、万、千、百、十对应的字母 }}结果测试
以上这两个测试结果呢,都是用的是题目给的测试例子,接下来的三个测试结果,都是我自己给出的测试例子,分别是800000000、888000000、800000008。
总结
总的来说,要理清楚这道题目的逻辑可不容易,需要静下心来,说来惭愧,这道题目我也是花了好长时间才理清楚逻辑,最后才勉强写出代码,还去网上查阅了相关资料,还是要继续努力,提升自己的编程能力。
标签: #用c语言计算存款利息