【项目Github地址】
【项目规划】
PSP表格
事项 |
预计时间(min) |
实际花费时间(min) |
需求分析 |
60 |
60 |
开发流程分析 |
30 |
60 |
新技术学习 |
300 |
400 |
实际工程开发 |
600 |
750 |
工程整体调试和优化 |
270 |
350 |
项目总结 |
60 |
120 |
(合计) |
1320 |
1740 |
【具体项目规划】
> 需求分析
本来打算用MFC的,后面再和组员讨论后决定使用Qt,因为可以跨平台。详细博客地址请见:http://www.cnblogs.com/ustctp/p/8711860.html
> 开发流程分析
- 程序基本架构为:主窗口(参数设计窗口)+子窗口(答题窗口,错题回顾窗口,成绩单窗口)
- 编程方式采用增量式编程,即每编完一个窗口即进行调试。
- 实现程序整体框架和核心功能时,詹元成为驾驶员,谭鹏为领航者;实现界面美化时,谭鹏为驾驶员,詹元成为领航者。实现接口对接时,詹元成为驾驶员,谭鹏为领航者。
> 代码规范(摘录)
- (代码风格)每一行开始处的缩进只能用Tab
- (代码风格)在代码行的结尾部分不能出现多余的空格
- (代码风格)除了特别情况,函数体内不能出现两个空行
- (代码风格)"if"、"for"、"while"、"do"、"try"、"catch" 等语句自占一行,执行语句不得紧跟其后。不论执行语句有多少都要加 "{ }" 。这样可以防止书写和修改代码时出现失误
- (代码风格)if语句如果有else语句,用 } else { 编写为一行,不推荐用 3 行代码的方式。
- (代码风格)多行变量定义,为了追求代码排版美观,可将变量竖向对齐。
- (代码风格)对于switch语句,若某个case不需要break一定要加注释声明。
- (命名规范)同一性:在编写一个子模块或派生类的时候,要遵循其基类或整体模块的命名风格,保持命名风格在整个模块中的同一性。
- (命名规范)标识符组成:标识符采用英文单词或其组合,应当直观且可以拼读,可望文知意,用词应当准确,避免用拼音命名。
- (命名规范)最小化长度 && 最大化信息量原则:在保持一个标识符意思明确的同时,应当尽量缩短其长度。
- (命名规范)避免过于相似:不要出现仅靠大小写区分的相似的标识符,例如"i"与"I","function"与"Function"等等。
- (命名规范)避免在不同级别的作用域中重名:程序中不要出现名字完全相同的局部变量和全局变量,尽管两者的作用域不同而不会发生语法错误,但容易使人误解。
- (命名规范)正确命名具有互斥意义的标识符:用正确的反义词组命名具有互斥意义的标识符,如:"nMinValue" 和 "nMaxValue","GetName()" 和"SetName()" ….
- (命名规范)避免名字中出现数字编号:尽量避免名字中出现数字编号,如Value1,Value2等,除非逻辑上的确需要编号。这是为了防止程序员偷懒,不肯为命名动脑筋而导致产生无意义的名字(因为用数字编号最省事)。
> 优化思路
- 界面美化(字体大小,字体,窗口扩展——支持滚动条的窗口)
- 功能完善
【项目细节】
> 接口定义
int error=0,error1=0; seti[0]; //题目数 seti[1]; //上限 seti[12]; //下限 seti[3]; //操作数数量 argu.integer = seti[3]; //支持整数 argu.fraction = seti[4]; //支持分数 argu.decimal = seti[5]; //不支持小数 argu.add = seti[6]; //支持加法 argu.sub = seti[7]; //支持减法 argu.multiply = seti[8]; //支持乘法 argu.division = seti[9]; //支持除法 argu.pow = seti[10]; //不支持乘方 argu.bracktet = seti[11]; //支持括号 error=Setting(seti[0],seti[1], argu); error=Setting(seti[0],seti[1],seti[2],seti[3],seti[4],seti[5],seti[6],seti[7],seti[8],seti[9],seti[10],seti[11]); error1=Generate(error);
> UI设计思路
- UI组的设计要求如下:
- 针对上述设计要求,我们将UI界面进行如下切分
- 主界面——参数设置界面(设置生成题目的数量,操作数的数量,题目及答案中的数值的范围等参数)
- 子界面1——答题界面(配有计数器)
- 子界面2——成绩展示界面(通过显示作答时间,正确率,分数等综合评定做题人的表现,并给出合适的评语)
- 子界面3——错题记录界面(展示做题过程中的错题以及超时的题目,方便做题人进行复习)
- 界面展示
(主界面——参数设置界面)
(子界面1——答题界面)
(子界面2——成绩分享界面)
(子界面3——错题记录界面)
(使用说明界面)
> 开发过程中的BUG及解决办法
【问题】
消息显示框中文显示乱码
【解决方案】
改变字符编码
// 采用文字编码转换类QTextCodec QTextCodec::setCodecForLocale(QTextCodec::codecForName("utf-8")); //如果是Qt4版本的,还可以设置tr进行中文转换 QTextCodec::setCodecForTr::QTextCodec::codecForName("utf-8")); //Windows下,一般情况下设置gb18030就可以显示中文了
【问题】
文件中无法写入中文
【解决方案】
采用QTextStream,而不用Qfile中自带的文件读取输出函数
#include <QtCore/QCoreApplication> #include <QFile> #include <QtDebug> #include <QTextStream> int main(int argc, char *argv[]) { QCoreApplication a(argc, argv); QFile file("test.txt"); //---参数:QFile::Truncate表示的是 将原文件内容清空, //--以WriteOnly方式打开文件,如果在工程文件下没有该txt文件,那么程序将创建该文件,若存在,则将原文件内容清空, if (file.open(QFile::WriteOnly | QFile :: Truncate)) { //---创建 QTextStream流操作对象, 使与QFile对象file绑定。 QTextStream out(&file); //----设置输出格式为: 居中,这里格式还可以设置为:right/left。 占10个字符; out << "socre:" << qSetFieldWidth(10) << center << 90 << endl; } else { qDebug() << "open file failed"; } file.close(); //---关闭文件~~~~~~ //-----输出提示信息 qDebug() << "1 writing data succesful 1" << endl; return a.exec(); }
【问题】
qt creator报错 error: C1083: 无法打开包括文件:“Untitle”: No such file or directory
【解决方案】
清理下项目。
菜单——build——run qmake
一定要执行qmake,不能只清理项目!!!!
> 对接过程的问题
- 不同Core组的通信方式不一样,有的是通过文件进行通信,而有的组是通过容器进行通信。(我们UI组这两种常见的通信方式都支持)
- 有的Core组是通过头文件和函数进行通信, 因此需要新建工程添加头文件和函数进行通信,也能够通信成功。
- 有的Core组Debug版和Release版都提供,有的只提供Release版,不过对接的时候这方面影响不大,不妨碍功能的正常执行。
【项目总结】
> 结对编程意义
- 结对编程可以提高工作效率|软件的内在复杂性决定了软件开发必然是一个复杂的脑力劳动过程。在完成个人作业时,有时为了急于完成任务,有了一点零星的想法就开始动工。所以上次就出现了由于前期设计的方案不合理而导致后期代码维护的噩梦。而在这次结对编程中,任何方案都是经过两个人激烈的讨论后产生的,这就有力的保证了设计和编码的质量。比如在进行需求分析时,我主张使用MFC进行界面开发,而小伙伴主张使用Qt,激烈的讨论之后最终选择了使用Qt作为我们组的开发工具,事实也证明Qt是正确高效的选择,因为Qt可以跨平台,而且IDE(Qt Creator)中的图形界面编辑工具非常友好,大大提升了编程效率(不过Qt Creator在字符编码上存在一些问题)。
- 结对编程促进团队建设|由于结对编程组织性强,因此可以有效地利用各种资源,进行最佳的组合。比如在此次结对编程中,我有Java的GUI开发经验,而我的小伙伴对C++相对较熟,因此我们两个上手Qt Creator很快。通过结对编程,我们俩的磨合速度很快,而且也很好的促进额团队中的沟通交流。在这样的团队里,大家都乐意互相协作,一起分享知识,分享快乐。
> 流程改善|团队项目流程完善
- 如果是一个团队进行软件开发,那么可以将软件的开发分为若干个部分,而每个部分由若干个2人小组共同开发。当然也不是所有的开发流程都需要结对编程,如果子项目的难度较低,那么单人开发即可。
- 比如我们的团队项目主要分为前端开发和后端开发,那么前端开发和后端开发中较难的开发部分可以用结对编程进行解决,而相对较简单的开发部分就由个人能力相对较强的同学完成。
> 结对编程应用|工作岗位
- 走上工作岗位后,会选择结对编程用于解决部分任务。
- 当软件公司在新员工加入时,一般都会有一段时间的培训,很多软件公司也会简历自己的知识库,看是很多新员工在面临实际的项目时仍然会不知所措,培训的效果微乎其微。而结对编程则会让新员工有机会与有经验的老员工一起共事,新员工学到的不仅是一些技术和技巧,更多的是他们思考问题,解决问题的方式。
- 软件攻击比较容易出现人员流动的问题,特别是老员工的离去,意味着公司多年的技术和业务积累的流失。而在结对编程的团队中,通过结对编程和结对伙伴的交换,知识不再是掌握在一个人的手中,而是整个团队一起共享。通过结对编程使公司的人员,技术和业务处于非常稳定的状态。
【课程意见】
- 项目博客要求以及课后作业内容偏多,考虑到学生课余时间有限,我觉得可以适当减少博客,课后作业内容要求,通过量的减少来换取质量的提高。
- 读书笔记可以取消评分制度,因为读书笔记主要是写给自己看的,自己有收获就好,他人的评分虽然可能会起到督促作用,但是收效甚微。