当前位置:文档之家› (完整版)C语言毕业课程设计报告【简易计算器设计】

(完整版)C语言毕业课程设计报告【简易计算器设计】

《C语言课程设计》报告设计题目:简单计算器设计学院名称:电子与信息工程学院专业:计算机科学与技术班级:计科09-1姓名:朱凯迪学号1 9指导教师:宋宏图定稿日期:2010年03月10日一、设计题目简单计算器设计二、设计要求在功能上功能尽量模拟windows操作系统中的计算器,系统界面不做强制要求。

三、设计目的①通过本项课程设计,可以培养独立思考、综合运用所学有关相应知识的能力,能更好的巩固《C语言程序设计》课程学习的内容,掌握工程软件设计的基本方法,强化上机动手编程能力,闯过理论与实践相结合的难关!更加了解了c语言的好处和其可用性!同时增加了同学之间的团队合作精神!更加也体会到以后在工作中团队合作的重要性和必要性!②通过C语言课程设计,使学生了解高级程序设计语言的结构,掌握基本的程序设计过程和技巧,掌握基本的分析问题和利用计算机求解问题的能力,具备初步的高级语言程序设计能力。

为后续各门计算机课程的学习和毕业设计打下坚实基础。

四、设计思想及过程①由于需要使功能尽量模仿Windows下的计算器,而很多功能要以图形界面实现,故用Borland C++Builder编写。

所以用的是面向对象程序设计。

但因为这是C语言的课程设计,所以除了面向对象的使用以外,所有语法都是按照C语言的格式编写。

②采用工程模式,文件包括calc.h(运算主函数头文件,包括各运算符的操作以及其辅助函数)、Main.h(窗体类的声明头文件)、Calc.cpp(工程初始化文件)、Main.cpp(代码主文件,包括各空间操作的函数)以及一些其它附属文件,包括dll动态链接库。

③在参考了Windows里的计算器以后,决定在我的课程设计中实现:⒈0~9的数字输入功能(小数点除外)⒉实现加、减、乘、整除、取模、阶乘、位运算左移、x的y次方、与、异或、x立方、x平方运算功能,二进制、八进制、十进制、十六进制转换功能,正负转换功能,退格、归零等功能。

⒊数字显示最多为40位,超过即用科学表示法表示(例如1E50)。

⒋运算时因最高能对5000位的数字进行运算,故所有功能建立在自行编写代码的高精度运算基础上。

④在按键操作中,先判断用户按的是数字键还是功能键。

功能键分运算符键、进制转换键以及清空键。

然后记录下来用户当前的按键,然后对上次按的功能键键进行运算。

如按了1、+、5,再按任何功能键即对1+5进行运算。

如果按的是进制转换键,就记录当前进制,则在以后每次操作中,都将显示结果转换为当前进制再显示。

如:以下是按5以及*号时的函数代码⑤对于高精度,采用结构体struct high{intnum[MAXN];};的形式,数组的一个元素存一位。

个位为num[1],将符号存在num[0]之中。

⒈对于高精度加法,先判断两个数符号,如果为异号,则进行高精度减法,否则将各位逐个相加,然后逐位进位,返回答案即可。

⒉对于高精度减法,先判断两个数符号,如果为异号,则进行高精度加法,否则用大数减小数,逐个相减,然后逐位退位,判断符号、返回答案即可。

⒊对于高精度乘法,用第二个数的各位乘以第一个数的各位。

然后错位相加,相当于小学生摆竖式。

最后将各位相乘的结果相加,逐位进位,判断符号、返回答案即可。

⒋对于高精度整除,采用各位从0~9枚举形式,如果此位与0~9相乘刚好小于等于相应数字,则为此位答案为这个数。

最后返回答案即可。

⒌对于高精度取模,则只需求出高精度整除,然后将数字减去整除的结果即可。

⒍对于n阶乘,做n次乘法,每乘一次,乘数减一。

⒎对于左移,虽然是建立在位运算基础上,但其效果只是乘以二,所以只需高精度乘以二即可。

⒏对于x的平方、立方、y次方,只需将x高精度相乘2次、3次或者更多次即可。

⒐对于与运算,先将两个数转换为二进制,然后对每位进行与运算,最后转换回十进制即可。

⒑对于异或运算,原理同与运算。

⑥对于进制转换,采用除n取余法。

将其转换为相应进制。

⑦对于清零键,按按键功能对actNum、ans、nowSym等变量清空或者减少一位即可。

⑧我对于程序容错性做了很大程度上的优化。

对于超出位数的运算会跳出“数字太大”提示。

对于各按键混合使用会导致的程序混乱用了极大程度上的优化,也就是说对于按键的随意性有很好的兼容性。

比如说可以直接按2再按*然后按=,就会算出2的平方。

⑨对于显示函数,先判断当前进制数,然后再将需要显示的数字转换为当前进制数再显示。

如果位数超过40,则取前几位,采用科学计数法显示。

⑩未能实现部分:小数部分。

由于时间关系,未能实现复制粘贴数字功能。

五、流程图六、运行过程打开Calc.exe,模拟Windows下的计算器功能。

①基本功能为输入数字,再输入运算符,然后输入运算符对应数字,按等号。

②输入数字,再输入运算符,输入等于号的结果为“当前输入的数字→运算符→当前输入的数字”。

可以调节正负号。

③输入“数字,运算符,数字,运算符...数字,运算符”亦可。

七、心得体会这次“简单计算器制作”的课程设计不仅让我对C语言的熟悉程度上升到了另一个高度,而且在一定意义上对面向对象设计的理解更加深刻了。

是我在编程路途上的一次质的飞跃。

而且在处理非常规数据类型的运算的锻炼下,使我对编程语言有了一个新的认识。

当看着一个具有图形界面的计算器的模型成品出现在自己面前时,心中有着无限感慨,原来编程也不是非常遥不可及的,原来在编程的趣味性中能让我学到更多有意思的知识。

附源程序清单:①Calc.h(运算函数集头文件)#include<stdio.h>#include<string>#include<string.h>#define HIGH struct high#define MAXN 5000#define MAXSHOW 40#define key_num 0#define key_sym 1struct high{int num[MAXN];};HIGH ans, actNum, nowShow;char nowSym = 'N', lastSym = 'N';bool _isincMed = true, _lastKey = key_num;int jz = 10;bool _isbig(HIGH a, HIGH b){int i;for(i = MAXN - 1; i > 0; i--){if(a.num[i] > b.num[i]) return true;elseif(a.num[i] < b.num[i]) return false;}return false;}void copy(char *str, char *rstr, int op, int len) //将str的从op开始的len个字符复制到rstr中{int i = 0, j = op - 1;for(; i <= len - 1 || str[j] == '\0'; i++, j++) rstr[i] = str[j];rstr[i] = '\0';}void copyint(HIGH num, HIGH *rint, int op, int len) //将str的从op开始的len个字符复制到rstr中{int i = 1, j = op;for(; i <= len && j < MAXN; i++, j++) rint -> num[i] = num.num[j];}void initNum(HIGH *numb) //初始化{int i;HIGH tmp;memset(tmp.num, 0, sizeof(tmp.num));*numb = tmp;}int absCmp(HIGH a, HIGH b) //比较绝对值大小{int i;for(i = MAXN - 1; i > 0; i--){if(a.num[i] != b.num[i]) return (a.num[i] > b.num[i]);}return -1;}int getMed(HIGH a) //获取位数{int i, med;for(i = MAXN - 1; i > 0; i--)if(a.num[i] != 0){med = i;break;}if(i == 0) med = 1;return med;}void turnSym(HIGH *a) //变号{a -> num[0] = a -> num[0] == 0 ? -1 : 0;}void decMed(HIGH *a) //减去一位{int i, med = getMed(*a);if(med == MAXN - 1) med--;for(i = 1; i <= med; i++) a -> num[i] = a -> num[i + 1];a -> num[med] = 0;}void incMed(HIGH *a, int b) //加一位{int i, med = getMed(*a);HIGH r;initNum(&r);if(med < MAXSHOW){for(i = 2; i <= med + 1; i++) r.num[i] = a -> num[i - 1];r.num[1] = b;r.num[0] = a -> num[0];}else r = *a;*a = r;}HIGH mul(HIGH a, HIGH b) //高精度乘法{int i, j, k, ma, mb;HIGH tmpr, r, zero;initNum(&zero);initNum(&r);ma = getMed(a);mb = getMed(b);for(i = 1; i <= ma; i++){initNum(&tmpr);for(j = 1; j <= mb; j++){tmpr.num[j] = a.num[i] * b.num[j];}int tmpMed = getMed(tmpr);if(tmpMed + i > MAXN){initNum(&r);Application -> MessageBox("数字太大!", "错误", MB_OKCANCEL);nowSym = 'N';_lastKey = key_num;lastSym = 'N';return r;}for(k = 1; k < tmpMed; k++){tmpr.num[k + 1] += (tmpr.num[k] / 10);tmpr.num[k] %= 10;}if(tmpr.num[tmpMed] > 10)tmpMed = getMed(tmpr);if(tmpMed + i > MAXN){initNum(&r);Application -> MessageBox("数字太大!", "错误", MB_OKCANCEL);nowSym = 'N';_lastKey = key_num;lastSym = 'N';return r;}for(j = 1; j <= tmpMed; j++) r.num[j + i - 1] += tmpr.num[j];}for(i = 1; i < MAXN - 1; i++){r.num[i + 1] += (r.num[i] / 10);r.num[i] %= 10;}if(r.num[MAXN - 1] > 9){initNum(&r);Application -> MessageBox("数字太大!", "错误", MB_OKCANCEL);nowShow = zero;nowSym = 'N';_lastKey = key_num;lastSym = 'N';return r;}if((a.num[0] == -1 && b.num[0] == -1) || (a.num[0] == 0&& b.num[0] == 0))r.num[0] = 0;else r.num[0] = -1;return r;}HIGH dec(HIGH a, HIGH b) //高精度减法{int i, med;HIGH r;HIGH inc(HIGH a, HIGH b);bool m = false;initNum(&r);if(a.num[0] == -1 && b.num[0] == -1) m = true;elseif(a.num[0] == -1){b.num[0] = -1;return inc(a, b);}elseif(b.num[0] == -1){a.num[0] = -1;return inc(a, b);}if(!absCmp(a, b)){a.num[0] = (a.num[0] == 0) ? -1 : 0;b.num[0] = (b.num[0] == 0) ? -1 : 0;return dec(b, a);}med = getMed(a);for(i = 1; i <= med; i++) r.num[i] = a.num[i] - b.num[i];for(i = 1; i <= med; i++){if(r.num[i] < 0){r.num[i + 1] -= 1;r.num[i] = 10 + r.num[i];}}if(m) r.num[0] = -1;return r;}HIGH inc(HIGH a, HIGH b) //高精度加法{int i;HIGH r, zero;bool m = false, err = false;initNum(&r);initNum(&zero);if(a.num[0] == -1 && b.num[0] == -1) m = true;elseif(a.num[0] == -1){a.num[0] = 0;return dec(b, a);}elseif(b.num[0] == -1){b.num[0] = 0;return dec(a, b);}for(i = 1; i < MAXN; i++) r.num[i] = a.num[i] + b.num[i];for(i = 1; i < MAXN - 1; i++){r.num[i + 1] += (r.num[i] / 10);r.num[i] %= 10;}if(r.num[MAXN - 1] > 9){initNum(&r);Application -> MessageBox("数字太大!", "错误", MB_OKCANCEL);nowSym = 'N';_lastKey = key_num;lastSym = 'N';nowShow = zero;return r;}if(m) r.num[0] = -1;return r;}HIGH div(HIGH a, HIGH b) //高精度整除{int i, j, ma = getMed(a), mb = getMed(b);HIGH r, tmpHigh, cmp, someZero, theone;initNum(&r);initNum(&theone);if(a.num[0] == b.num[0]) ;else r.num[0] = -1;a.num[0] = 0;b.num[0] = 0;for(i = ma - mb + 1; i > 0; i--){initNum(&tmpHigh);copyint(a, &tmpHigh, i, ma);initNum(&cmp);for(j = 0; !_isbig(cmp, tmpHigh); j++){cmp = inc(cmp, b);}theone.num[1] = j;if(_isbig(mul(theone, b), tmpHigh)) j--;r.num[i] = j;initNum(&someZero);someZero.num[i] = j;someZero = mul(someZero, b);a = dec(a, someZero);}return r;}HIGH mod(HIGH a, HIGH b) //高精度取模{int i, j;HIGH tmpans;tmpans = div(a, b);return dec(a, mul(tmpans, b));}String getHexStr(int a) //得到十六进制字符串{if(a == 10) return "A";elseif(a == 11) return "B";elseif(a == 12) return "C";elseif(a == 13) return "D";if(a == 14) return "E";elseif(a == 15) return "F";}int getHex(HIGH a) //十六进制取余{if(a.num[2] == 0) return a.num[1];else return a.num[2] * 10 + a.num[1];}HIGH hex(HIGH a) //转化十六进制{int i = 0, j;HIGH zero, r, sixteen;initNum(&zero);initNum(&r);initNum(&sixteen);sixteen.num[1] = 6;sixteen.num[2] = 1;if(a.num[0] == -1){initNum(&r);Application -> MessageBox("不能为负数!", "错误", MB_OKCANCEL);nowSym = 'N';_lastKey = key_num;lastSym = 'N';nowShow = zero;return r;}while(_isbig(a, zero))i++;r.num[i] = getHex(mod(a, sixteen));a = div(a, sixteen);if(getMed(r) > MAXSHOW){initNum(&r);Application -> MessageBox("数字太大!", "错误", MB_OKCANCEL);nowShow = zero;nowSym = 'N';_lastKey = key_num;lastSym = 'N';return r;}}return r;}HIGH bajinzhi(HIGH a) //转化八进制{int i = 0, j;HIGH zero, r, eight;initNum(&zero);initNum(&r);initNum(&eight);eight.num[1] = 8;if(a.num[0] == -1){initNum(&r);Application -> MessageBox("不能为负数!", "错误", MB_OKCANCEL);nowSym = 'N';_lastKey = key_num;lastSym = 'N';nowShow = zero;return r;}while(_isbig(a, zero)){i++;r.num[i] = mod(a, eight).num[1];a = div(a, eight);if(getMed(r) > MAXSHOW){initNum(&r);Application -> MessageBox("数字太大!", "错误", MB_OKCANCEL);nowShow = zero;nowSym = 'N';_lastKey = key_num;lastSym = 'N';return r;}}return r;}HIGH bin(HIGH a) //转化二进制{int i = 0, j;HIGH zero, r, two;initNum(&zero);initNum(&r);initNum(&two);two.num[1] = 2;if(a.num[0] == -1){initNum(&r);Application -> MessageBox("不能为负数!", "错误", MB_OKCANCEL);nowShow = zero;nowSym = 'N';_lastKey = key_num;lastSym = 'N';return r;}while(_isbig(a, zero)){i++;r.num[i] = a.num[1] % 2;a = div(a, two);if(getMed(r) > MAXSHOW){initNum(&r);Application -> MessageBox("数字太大!", "错误", MB_OKCANCEL);nowShow = zero;nowSym = 'N';_lastKey = key_num;lastSym = 'N';return r;}}return r;}HIGH binToshi(HIGH a){int i, med = getMed(a);HIGH r, tmp, the1, tmp2, two, thetwo;initNum(&tmp);initNum(&tmp2);initNum(&the1);initNum(&thetwo);initNum(&two);two.num[1] = 1;thetwo.num[1] = 2;the1.num[1] = 1;initNum(&r);for(i = 1; i <= med; i++, tmp = inc(tmp, the1)) {tmp2.num[1] = a.num[i];r = inc(r, mul(tmp2, two));two = mul(two, thetwo);}return r;}HIGH and(HIGH a, HIGH b) //与{HIGH tmpa, tmpb, r;int med, meda, medb, i;initNum(&r);tmpa = bin(a);tmpb = bin(b);meda = getMed(tmpa);medb = getMed(tmpb);med = (meda > medb) ? meda : medb;for(i = 1; i <= med; i++)r.num[i] = tmpa.num[i] & tmpb.num[i];。

相关主题