逻辑表达式课程设计报告

中北大学

课程设计报告

学期

学 院: 信息与通信工程学院 专 业: 电子信息科学与技术 学 生 姓 名: 向 伟

学 号: 1505044245 课程设计题目: 逻辑表达式的合理性判断 起 迄 日 2016年 12 月 12 日~2016 年12 月 30 日

课程设计地点: 科学楼五院106 指 导 教 师: 李建民

提交报告日期: 2016 年 月 日

设计要求

一、逻辑表达式的合理性判断

任务:(自己解析后的具体任务); ◆ 编写键盘输入与文件读取表达式的程序; ◆ 编写可以依次进行识别判断表达式的程序;

◆ 整理表达式错误类型,并且编写分类进行错误原因分析的提示程序; ◆ 编写扫描表达式的程序;

◆ 分类编写检测逻辑运算符,操作数以及括号是否合法的程序; ◆ 编写删除所有空格操作的程序

二、要求(自己程序能达到的指标)

◆ 表达式既能手动输入,又能从文件中读取,并且能有多个表达式;

◆ 可以输入任意表达式(含所有可输入的字符及符号),程序将进行自动

判别是否为逻辑表达式; ◆ 能自动删除所有空格;

◆ 程序可以分析输入的表达式的所有错误类型并输出到显示器上; ◆ 程序优先对括号合法性进行判断,包含所有括号的组合情况;

算法分析与程序详解

一、整体结构

整个程序分为:表达式数据的读取,空格删除,括号(多重)的扫描判断与记录,运算符的扫描与检测,操作数的扫描与检测。

二、各个函数的详细说明:

1.Deletespace 函数,传入表达式字符数组,以及字符坐标,循环检测并删除空格,每次调用完该函数后继续检查当前坐标位置是否为空格,若仍然为空格将继续调用该函数,直至当前位置不再是空格,将继续循环检测下一个坐标。

2.Getmount 函数:为了解决scanf 函数和gets 函数同时使用时产生的bug (若使用了前者再使用或者,或者将会自动接收前者的一个换行符,导致后者第一个数

据无法正常输入),使用该函数将输入的字符数字通过ASCII 码转换成整型数字。

3.Operator 函数:在对表达式进行从头至尾的扫描过程中若匹配到含逻辑运算符的字符,则返回成功,否则返回失败,并输出错误类型的提示信息,本次判断将就此结束。

4.Bracket 函数:从左至右扫描过程中,发现括号后检查括号是否合法,若合法,用一个二维数组记录检测到的合法括号的位置信息,并且返回此信息,若不合法,返回不合法类型,并且输出错误类型的提示信息,本次判断将就此结束。

5.Repeat 函数:主要检查是否含有重复的无用括号,例如“((xxx ))”,具体方法是,设置该函数返回的缺省值是有重复,在循环检测的过程中,分别用两个数组记录连续的左右括号的位置,然后用两个for 循环实现从左括号位置到右括号位置的交叉扫描,如果出现了括号,则修改缺省值为没有重复,并且立刻跳出内部for 循环的扫描,进行外层for 循环的下一次扫描,如果某次内部扫描完毕后都没有出现括号,则缺省值不会被修改,将直接跳出外层循环,并且返回有重复,输出错误类型提示,结束本次判断。

6.Scan 函数:扫描运算符的函数,其扫描方式为根据Bracket 函数和提供的位置进行扫描,如果匹配到运算符,并且检测到该运算符合法,将调用相关运算符检测函数,进行运算符的检测。

7.Single 函数:一元运算符及操作数检测函数,根据一元运算符的特征进行判断该运算符到附近的运算符或者前面左括号后面右括号之间的操作数是否合法,规定操作数为字母或字母组合为合法。若后面紧接着出现左括号则也认为操作数合法。

8. Double 函数:二元运算符及操作数检测函数,根据二元运算符的特征进行判断该运算符到附近的运算符或者前面左括号后面右括号之间的操作数是否合法,规定操作数为字母或字母组合为合法。若后面紧接着出现左括号或者前面紧接着出现右括号则也认为操作数合法。

三、程序运行过程

每个函数具体如何工作请参考第二部分对各个函数的详细说明。 程序从主函数开始运行,首先进入数据来源方式的选择,用变量select 表示,输入1或2分别进入文件读取数据和键盘输入数据的程序模块,在读取到数据后,进入删除空格函数Deletespace 函数删除空格后返回新的数据,紧接着调用Operator 函数,检测是否存在运算符,若没有则返回该错误类型,若有则进入Bracket 函数对括号进行扫描,若有括号,括号没有正常成对,则返回该错误类型,若没有括号,将直接从表达式开始到表达式结尾进行Scan 函数扫描,若有括号,且成对,则调用Repeat 函数进行多余重复括号检查,若存在多余括号,则返回该错误类型,若不存在,则返回Bracket 函数生成的括号坐标位置信息,

并根据该信息进行循环Scan 函数扫描,如果匹配到运算符,并且检测到该运算符合法,根据运算符类型的不同选择调用Single 函数(一元运算符)和Double 函数(二元运算符),进行操作数检查,若不合法则返回相应错误类型,若合法,则返回正确。

另外第五部分附有流程图

四、错误类型说明

五、流程图

1、表达式数据的读取

2. 空格删除操作

当发现当前表达式中有空格时,调用Deletespace(char (*string)[m],int i,int j) 函数

六、运行结果

利用文件读取各种错误类型的表达式如下:(按每行四个表达式列出,表达式间用换行隔开)

saff && asdf !(fs||fsf)& &da fs!#fs (f||(s|||dfs)) f||(s|%fsf) (fs!#fs) fsd!fas fds(!fs||da) saf3||dad adaf||sf2+h adaf||sf2+h !d(asd) ||sa sdaf|| fa||(dad||d)

其程序运行部分结果如下图

举例说明:

1. 如输入: cd|| (fs||da)表达式,经过Deletespace 函数删除空格后返回新的表达式为 cd||(fs||da),然后进行Operator 函数检查是否存在操作符,此处存在,则调用Repeat 函数进行多余重复括号检查,此处不存在,则进入Bracket 函数对括号进行扫描,此处有括号,并且记录括号位置4、11,然后调用Repeat 函数进行多余重复括号检查,此处无多余括号,然后根据坐标位置信息进行循环Scan 函数扫描,此处扫描到“||”,为二元运算符,则调用Double 函数,进行操作数检查,前面为fs ,后面为“da ”, 均为合法操作数,括号内部扫描完毕后,扫描括号外部,从位置0到位置4,此处扫描到“||”,为二元运算符,则调用Double 函数,进行操作数检查,前面为“cd ”,后面为“(”, 均为合法操作数,最后在位置13扫描到结束符,则结束当前表达式扫描,并且返回正确提示,进行下一个表达式判断。

2. 如输入saff asdf 表达式,经过Deletespace 函数删除空格后返回新的表达式为saff asdf,然后进行Operator 函数检查是否存在操作符,此处不存在,则返回“第1个表达式没有逻辑运算符”的错误提示,并且结束当前表达式判断,进入下一个表达式的判断。

七、总结

技术方面:

1. 良好的编程习惯真的很重要,它可以帮助自己减少错误率,还能更好更快地回看和理自己的程序,大大提高程序的可读性。比如写好注释和较好的排版。

2. 注意变量的生命周期,既能节省内存资源,又可以避免变量赋值不正确。 3. 编写程序前应该先整理需要考虑的所有情况,包括特殊情况,避免出现bug 。

4. 除了使用编程环境自带的调试功能逐步或断电调试程序外,还可以自己在程序中适当位置通过屏幕输出提示进行调试。

5. 尽量使用最优算法,既能提高自己的思维能力,又能使程序简洁而高效。 6. 要给每一个函数起一个好名称,做到见名知义的程度方便对程序整体的快速理解。

7. 在编写一个项目或程序时应事先考虑到需要定义的函数,把且有相同功能的部分抽象到一个函数时,减少代码冗余。如本程序中的Scan 函数。

8. 一个函数应该只解决一个功能或问题。 心得体会方面:

通过近两周的奋斗,课程设计接近了尾声。经过两周的奋战我们的课程设计终于完成了。在没有做课程设计以前觉得课程设计只是对C 语言这门课程所学知识的单纯总结,但是通过这次做课程设计发现自己的看法有点太片面。课程设计不仅是对前面所学知识的一种检验,而且也是对自己能力的一种提高。通过这次课程设计使我们明白了自己原来知识还比较欠缺。自己要学习的东西还太多,以前老是觉得自己什么东西都会,什么东西都懂,有点眼高手低。通过这次课程设计,我们才明白学习是一个长期积累的过程,在以后的工作、生活中都应该不断的学习,提高自己的知识和综合素质。

在这次课程设计中也使我们们的同学关系更进一步了,同学之间互相帮助,有什么不懂的大家在一起商量,听听不同的看法对我们们更好的理解知识,所以在这里非常感谢帮助我们的同学。

总之,大家都认为万事开头难,不知道如何入手。最后终于做完了有种如释重负的感觉。此外,还得出一个结论:知识必须通过应用才能实现其价值!有些东西以为学会了,但真正到用的时候才发现是两回事,所以我们认为只有到真正会用的时候才是真的学会了。通过这次课程设计,我们们即学会了使用VC6.0软件和codeblocks 软件,也掌握了一些有用的知识,这对我们们以后的学习和生活非常的有帮助,也使得我们们对自己的总体知识水平有了一个了解。懂得了知识的重要性。使我们学会了如何运用所学的知识收集、归纳相关资料解决具体问题的方法,加强了我们的动手能力、分析和解决问题的能力、以及增强综合运用知识的能力。同时对自己应用计算机的水平有了一个更深刻的了解,我们在今后的学习和生活中,可以有针对性的学习和改善。

在此要感谢我们的指导老师李老师对我们的悉心的指导,感谢老师给我们的帮助。在设计过程中,我们通过查阅大量有关资料,与同学交流经验和自学,并向老师请教等方式,使自己学到了不少知识,也经历了不少艰辛,但收获同样巨大。在整个设计中我们懂得了许多东西,也培养了我们独立工作的能力,树立了对自己工作能力的信心,相信会对今后的学习工作生活有非常重要的影响。而且大大提高了动手的能力,使我们充分体会到了在创造过程中探索的艰难和成功时的喜悦。虽然这个设计做的也不太好,但是在设计过程中所学到的东西是这次课程设计的最大收获和财富,使我们终身受益。

中北大学

课程设计报告

学期

学 院: 信息与通信工程学院 专 业: 电子信息科学与技术 学 生 姓 名: 向 伟

学 号: 1505044245 课程设计题目: 逻辑表达式的合理性判断 起 迄 日 2016年 12 月 12 日~2016 年12 月 30 日

课程设计地点: 科学楼五院106 指 导 教 师: 李建民

提交报告日期: 2016 年 月 日

设计要求

一、逻辑表达式的合理性判断

任务:(自己解析后的具体任务); ◆ 编写键盘输入与文件读取表达式的程序; ◆ 编写可以依次进行识别判断表达式的程序;

◆ 整理表达式错误类型,并且编写分类进行错误原因分析的提示程序; ◆ 编写扫描表达式的程序;

◆ 分类编写检测逻辑运算符,操作数以及括号是否合法的程序; ◆ 编写删除所有空格操作的程序

二、要求(自己程序能达到的指标)

◆ 表达式既能手动输入,又能从文件中读取,并且能有多个表达式;

◆ 可以输入任意表达式(含所有可输入的字符及符号),程序将进行自动

判别是否为逻辑表达式; ◆ 能自动删除所有空格;

◆ 程序可以分析输入的表达式的所有错误类型并输出到显示器上; ◆ 程序优先对括号合法性进行判断,包含所有括号的组合情况;

算法分析与程序详解

一、整体结构

整个程序分为:表达式数据的读取,空格删除,括号(多重)的扫描判断与记录,运算符的扫描与检测,操作数的扫描与检测。

二、各个函数的详细说明:

1.Deletespace 函数,传入表达式字符数组,以及字符坐标,循环检测并删除空格,每次调用完该函数后继续检查当前坐标位置是否为空格,若仍然为空格将继续调用该函数,直至当前位置不再是空格,将继续循环检测下一个坐标。

2.Getmount 函数:为了解决scanf 函数和gets 函数同时使用时产生的bug (若使用了前者再使用或者,或者将会自动接收前者的一个换行符,导致后者第一个数

据无法正常输入),使用该函数将输入的字符数字通过ASCII 码转换成整型数字。

3.Operator 函数:在对表达式进行从头至尾的扫描过程中若匹配到含逻辑运算符的字符,则返回成功,否则返回失败,并输出错误类型的提示信息,本次判断将就此结束。

4.Bracket 函数:从左至右扫描过程中,发现括号后检查括号是否合法,若合法,用一个二维数组记录检测到的合法括号的位置信息,并且返回此信息,若不合法,返回不合法类型,并且输出错误类型的提示信息,本次判断将就此结束。

5.Repeat 函数:主要检查是否含有重复的无用括号,例如“((xxx ))”,具体方法是,设置该函数返回的缺省值是有重复,在循环检测的过程中,分别用两个数组记录连续的左右括号的位置,然后用两个for 循环实现从左括号位置到右括号位置的交叉扫描,如果出现了括号,则修改缺省值为没有重复,并且立刻跳出内部for 循环的扫描,进行外层for 循环的下一次扫描,如果某次内部扫描完毕后都没有出现括号,则缺省值不会被修改,将直接跳出外层循环,并且返回有重复,输出错误类型提示,结束本次判断。

6.Scan 函数:扫描运算符的函数,其扫描方式为根据Bracket 函数和提供的位置进行扫描,如果匹配到运算符,并且检测到该运算符合法,将调用相关运算符检测函数,进行运算符的检测。

7.Single 函数:一元运算符及操作数检测函数,根据一元运算符的特征进行判断该运算符到附近的运算符或者前面左括号后面右括号之间的操作数是否合法,规定操作数为字母或字母组合为合法。若后面紧接着出现左括号则也认为操作数合法。

8. Double 函数:二元运算符及操作数检测函数,根据二元运算符的特征进行判断该运算符到附近的运算符或者前面左括号后面右括号之间的操作数是否合法,规定操作数为字母或字母组合为合法。若后面紧接着出现左括号或者前面紧接着出现右括号则也认为操作数合法。

三、程序运行过程

每个函数具体如何工作请参考第二部分对各个函数的详细说明。 程序从主函数开始运行,首先进入数据来源方式的选择,用变量select 表示,输入1或2分别进入文件读取数据和键盘输入数据的程序模块,在读取到数据后,进入删除空格函数Deletespace 函数删除空格后返回新的数据,紧接着调用Operator 函数,检测是否存在运算符,若没有则返回该错误类型,若有则进入Bracket 函数对括号进行扫描,若有括号,括号没有正常成对,则返回该错误类型,若没有括号,将直接从表达式开始到表达式结尾进行Scan 函数扫描,若有括号,且成对,则调用Repeat 函数进行多余重复括号检查,若存在多余括号,则返回该错误类型,若不存在,则返回Bracket 函数生成的括号坐标位置信息,

并根据该信息进行循环Scan 函数扫描,如果匹配到运算符,并且检测到该运算符合法,根据运算符类型的不同选择调用Single 函数(一元运算符)和Double 函数(二元运算符),进行操作数检查,若不合法则返回相应错误类型,若合法,则返回正确。

另外第五部分附有流程图

四、错误类型说明

五、流程图

1、表达式数据的读取

2. 空格删除操作

当发现当前表达式中有空格时,调用Deletespace(char (*string)[m],int i,int j) 函数

六、运行结果

利用文件读取各种错误类型的表达式如下:(按每行四个表达式列出,表达式间用换行隔开)

saff && asdf !(fs||fsf)& &da fs!#fs (f||(s|||dfs)) f||(s|%fsf) (fs!#fs) fsd!fas fds(!fs||da) saf3||dad adaf||sf2+h adaf||sf2+h !d(asd) ||sa sdaf|| fa||(dad||d)

其程序运行部分结果如下图

举例说明:

1. 如输入: cd|| (fs||da)表达式,经过Deletespace 函数删除空格后返回新的表达式为 cd||(fs||da),然后进行Operator 函数检查是否存在操作符,此处存在,则调用Repeat 函数进行多余重复括号检查,此处不存在,则进入Bracket 函数对括号进行扫描,此处有括号,并且记录括号位置4、11,然后调用Repeat 函数进行多余重复括号检查,此处无多余括号,然后根据坐标位置信息进行循环Scan 函数扫描,此处扫描到“||”,为二元运算符,则调用Double 函数,进行操作数检查,前面为fs ,后面为“da ”, 均为合法操作数,括号内部扫描完毕后,扫描括号外部,从位置0到位置4,此处扫描到“||”,为二元运算符,则调用Double 函数,进行操作数检查,前面为“cd ”,后面为“(”, 均为合法操作数,最后在位置13扫描到结束符,则结束当前表达式扫描,并且返回正确提示,进行下一个表达式判断。

2. 如输入saff asdf 表达式,经过Deletespace 函数删除空格后返回新的表达式为saff asdf,然后进行Operator 函数检查是否存在操作符,此处不存在,则返回“第1个表达式没有逻辑运算符”的错误提示,并且结束当前表达式判断,进入下一个表达式的判断。

七、总结

技术方面:

1. 良好的编程习惯真的很重要,它可以帮助自己减少错误率,还能更好更快地回看和理自己的程序,大大提高程序的可读性。比如写好注释和较好的排版。

2. 注意变量的生命周期,既能节省内存资源,又可以避免变量赋值不正确。 3. 编写程序前应该先整理需要考虑的所有情况,包括特殊情况,避免出现bug 。

4. 除了使用编程环境自带的调试功能逐步或断电调试程序外,还可以自己在程序中适当位置通过屏幕输出提示进行调试。

5. 尽量使用最优算法,既能提高自己的思维能力,又能使程序简洁而高效。 6. 要给每一个函数起一个好名称,做到见名知义的程度方便对程序整体的快速理解。

7. 在编写一个项目或程序时应事先考虑到需要定义的函数,把且有相同功能的部分抽象到一个函数时,减少代码冗余。如本程序中的Scan 函数。

8. 一个函数应该只解决一个功能或问题。 心得体会方面:

通过近两周的奋斗,课程设计接近了尾声。经过两周的奋战我们的课程设计终于完成了。在没有做课程设计以前觉得课程设计只是对C 语言这门课程所学知识的单纯总结,但是通过这次做课程设计发现自己的看法有点太片面。课程设计不仅是对前面所学知识的一种检验,而且也是对自己能力的一种提高。通过这次课程设计使我们明白了自己原来知识还比较欠缺。自己要学习的东西还太多,以前老是觉得自己什么东西都会,什么东西都懂,有点眼高手低。通过这次课程设计,我们才明白学习是一个长期积累的过程,在以后的工作、生活中都应该不断的学习,提高自己的知识和综合素质。

在这次课程设计中也使我们们的同学关系更进一步了,同学之间互相帮助,有什么不懂的大家在一起商量,听听不同的看法对我们们更好的理解知识,所以在这里非常感谢帮助我们的同学。

总之,大家都认为万事开头难,不知道如何入手。最后终于做完了有种如释重负的感觉。此外,还得出一个结论:知识必须通过应用才能实现其价值!有些东西以为学会了,但真正到用的时候才发现是两回事,所以我们认为只有到真正会用的时候才是真的学会了。通过这次课程设计,我们们即学会了使用VC6.0软件和codeblocks 软件,也掌握了一些有用的知识,这对我们们以后的学习和生活非常的有帮助,也使得我们们对自己的总体知识水平有了一个了解。懂得了知识的重要性。使我们学会了如何运用所学的知识收集、归纳相关资料解决具体问题的方法,加强了我们的动手能力、分析和解决问题的能力、以及增强综合运用知识的能力。同时对自己应用计算机的水平有了一个更深刻的了解,我们在今后的学习和生活中,可以有针对性的学习和改善。

在此要感谢我们的指导老师李老师对我们的悉心的指导,感谢老师给我们的帮助。在设计过程中,我们通过查阅大量有关资料,与同学交流经验和自学,并向老师请教等方式,使自己学到了不少知识,也经历了不少艰辛,但收获同样巨大。在整个设计中我们懂得了许多东西,也培养了我们独立工作的能力,树立了对自己工作能力的信心,相信会对今后的学习工作生活有非常重要的影响。而且大大提高了动手的能力,使我们充分体会到了在创造过程中探索的艰难和成功时的喜悦。虽然这个设计做的也不太好,但是在设计过程中所学到的东西是这次课程设计的最大收获和财富,使我们终身受益。


相关文章

  • 数字电路实验(1)基础实验
  • 电子技术基础实验(二)2.1 集成门电路的逻辑功能与QII应用 哈尔滨工程大学信息与通信工程学院 电子技术基础教研室  课程介绍 实验室守则 实验考核 实验内容 2.1.1. 2014092100 课程介绍 简介 课程介绍 2009 ...查看


  • 8421码到余三循环码的转换电路仿真课设报告
  • 东北大学秦皇岛分校计算机与通信工程院 电子线路课程设计 具有数显的数码转换电路(8421码-余3循环码 ) 课程设计任务书 专业:通信工程 学号:4101015 学生姓名:吴玉新 设计题目:具有数显的码制转换电路8421码-余3循环码 一. ...查看


  • 课程设计报告框架
  • 课程设计(实习)评审表 课程设计(实习)作品验收表 注:1. 除"验收情况"栏外,其余各栏均由学生在作品验收前填写. 2. "验收情况"栏由验收小组按实际验收的情况如实填写. 按照如下形式生成目录,正 ...查看


  • 数电课程设计报告-抢答器
  • 课程设计报告 题 目 数字抢答器设计 课 程 名 称 数字电子技术 院 部 名 称 机电工程学院 专 业 电气工程及其自动化 班 级 10电气1 学 生 姓 名 管志成 学 号 1004103027 课程设计地点 C206 课程设计学时 1 ...查看


  • 抢答器实验报告 1
  • 内蒙古师范大学计算机与信息工程学院 <数字逻辑>综合课程设计报告 智力竞赛抢答器逻辑电路设计 计算机与信息工程学院 10级师范汉班 XXX 2010110 XXX 指导教师 XXX 讲师 摘要 现今,形式多样.功能完备的抢答器已 ...查看


  • 译码器实验报告
  • 课程编号: 深 圳 大 学 实 验 报 告 课程名称: 数字电路 实验名称: 译码器 学 院: 信息工程学院 指导教师: 刘静 报告人: 李金梁 组号: 03 学号: 2013130025 实验地点: n102 实验时间: 2014年 10 ...查看


  • 数据结构A教学大纲
  • 数据结构A 教学大纲 (Data Structures A) 课程编号: 06311360 学 分: 5.0 学 时: 75 (其中:讲课学时:60 实验学时:0 上机学时:15) 先修课程:离散数学.程序设计基础.面向对象程序设计 适用专 ...查看


  • 数据库系统原理04735课后习题参考答案
  • 数据库系统原理04735课后习题答 第一章. 数据库系统基本概念 1.1. 名词解释 DB --DB 是长期存储在计算机内.有组织的.统一管理的相关数据的集合.DB 能为各种用户共享,具有较小冗余度.数据间联系紧密而又有较高的数据独立性等特 ...查看


  • 汽车尾灯设计
  • 淮海工学院 课程设计报告书 课程名称: 数电技术课程设计 题 目: 汽车尾灯控制器的设计 系 (院): 电子工程学院 学 期: 2011-2012-2 专业班级: 电子101 姓 名: 王琛 学 号: 031091121 1. 设计目的及主 ...查看


热门内容