结队作业
一 前言:
应该感谢我的队友,让我得到了充分锻炼的机会,以及增长了一些人生经验。
二 代码地址
https://git.coding.net/laolaf/nidayeproject.git
三 PSP
注:只是本人的计划时间和完成时间,原计划是只完成计算模块。
|
PSP2.1 |
任务内容 |
计划时间(min) |
实际时间 |
|
Planning |
计划 |
20 |
70 |
|
Estimate |
估计这个任务需要多少时间,并规划大致工作步骤 |
800 |
1075 |
|
Analysis |
需求分析 (包括学习新技术) |
40 |
50 |
|
Design Spec |
生成设计文档 |
20 |
20 |
|
Design Review |
设计复审 (和同事审核设计文档) |
20 |
20 |
|
Coding Standard |
代码规范 (为目前的开发制定合适的规范) |
10 |
5 |
|
Design |
具体设计 |
40 |
50 |
|
Coding |
具体编码 |
800 |
800 |
|
Code Review |
代码复审 |
20 |
30 |
|
Test |
测试(自我测试,修改代码,提交修改) |
15 |
15 |
|
Reporting |
报告 |
20 |
40 |
|
Test Report |
测试报告 |
10 |
40 |
|
Size Measurement |
计算工作量 |
10 |
5 |
四 接口设计
1)Information Hiding:
开发软件的过程中,Information Hiding可以比较理想地完成对信息的封装,在每个模块里封装了不同的程序,达成了对每一模块内部信息的隐蔽。这样,即使不知道某模块内部,也可以对项目进行模块化的处理和分析。
2)Loose Coupling:
松耦合通过接口的方式实现各个原本有联系的模块之间的调用,比如逻辑层和业务层分开,这样可以使逻辑层出错时,不会影响到业务层。
3)
对于接口我的理解是:用于实现功能的一个没有实现功能的特殊的类,它本身是一系列操作的集合,但它是没有完成什么的,是功能函数的原型,不同的接口拼接到主类里,实现最终的功能。本项目里,gui中的guitime,guidel,Create2和Cal都可以看做接口,几个模块之间不知道它们的内部细节也是无妨的。
Command:用于命令行测试,主要内容是参数的接收以及错误抛出。
Create2:其中的Create(int n, int m1, int m2,int o)方法按照要求定制算式。
Cal:计算,在Command和gui类里可重复调用。
gui:
gui设计的时候没有严格区分出题和做题的界面。
1 guitime:计算做题时间,主界面会有计时器按钮,点击之后会再跳出一个有着“begin/开始”和“stop/结束”按钮的界面,点击之后进入倒计时。
2 guimain:简体汉语界面。它的三个按钮分别来调用guicreate,guidel,guitime,并且通过ArrayList list1和answer记录来判断做题对错的正确率。
3 guidel:作为选择界面,在该界面里有三个按钮:中文简体,中文繁体,英语,用于选择语言。
4 guiEnglish:英语界面,和汉语界面代码相似。
5 gui3:中文繁体界面。

五 性能分析
性能已经改进,Cal和Create方法在ui层和Command里重复调用。

六 单元测试
对Create2的核心代码的单元测试:


对Create2的测试的量化结果:

对guimain的测试的量化结果:


对guitime的测试的量化结果:

七 模块异常处理
异常处理有五种,分别对参数输入错误(数字变字母),对m的输入大小范围有误,m后两个参数大小颠倒,对n的输入n的大小范围出问题,参数o的范围大小有问题(应该的范围:1到10),而这些代码的写法都差不多,因此就展示抛出参数错误的代码。(这里的抛出我是直接打印在黑窗上了,直接抛出可能会被当成Command本身出了问题。)
public static void parameter1Error(String ex,int i)throws Exception{ ArrayList<String> ma= new ArrayList<String>(); ma.add("-n");ma.add("-m"); ma.add("-o");ma.add("-c"); ma.add("-b");
if(!ma.contains(ex)){ System.out.println("参数错误,重新输入"); } }



八 界面模块详细设计
设计了四个界面:guidel,guimain,guiEnglish,gui3。通过在guidel选择进入不同语言的模块,以guimain为例, guimain调用guitime,guidel,Create2,Cal的代码,通过按钮buttton-1以及它的监听类addActionListener通过把题目存到list1,把答案存到answer,最后在textArea里输出,完成记录题目和判断答案对错功能。点击“确定”按钮则开始判断,点击“生成文件”按钮则生成在root目录里的result.txt。guiEnglish和gui3同理
JButton button_1 = new JButton("提交答案");
button_1.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
String[] ans =textArea_1.getText().split("\n");
String strings[]=new String[list11.size()];
for(int i=0,j=list11.size();i<j;i++){
strings[i]=list11.get(i);
} int count=0;
for(int i = 0;i < list11.size();i++){
//answer.add(ans[i]+"");}
//for(String str1:answer)
//{
if(ans[i].equals(strings[i]))
{
print.add("对\n");
count++;
}
else{print.add("错\n");}
}
//for(int i=0,j=print.size();i<j;i++){
textArea_2.append(print+"\n");
double sum =((double)count/(double)(list11.size()))*100;
lblNewLabel.setText("正确率:"+sum+"%");
// String [] print1=print;
//}
}
});
JButton btnSubmitAnswer = new JButton("Submit answer");
btnSubmitAnswer.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
String[] ans =textArea_1.getText().split("\n");
String strings[]=new String[list11.size()];
for(int i=0,j=list11.size();i<j;i++){
strings[i]=list11.get(i);
} int count=0;
for(int i = 0;i < list11.size();i++){
//answer.add(ans[i]+"");}
//for(String str1:answer)
//{
if(ans[i].equals(strings[i]))
{
print.add("Right\n");
count++;
}
else{print.add("Wrong\n");}
}
//for(int i=0,j=print.size();i<j;i++){
textArea_2.append(print+"\n");
double sum =((double)count/(double)(list11.size()))*100;
lblNewLabel.setText("Accuracy:"+sum+"%");
// String [] print1=print;
//}
}
});
btnSubmitAnswer.setBounds(30, 236, 124, 23);
contentPane.add(btnSubmitAnswer);
getContentPane().setLayout(null);
JScrollPane scrollPane = new JScrollPane();
scrollPane.setBounds(20, 49, 146, 177);
contentPane.add(scrollPane);
scrollPane.setViewportView(textArea);
textArea.setBackground(UIManager.getColor("Button.background"));
textArea.setFont(new Font("MS Gothic", Font.PLAIN, 18));
JScrollPane scrollPane_1 = new JScrollPane();
scrollPane_1.setBounds(176, 49, 62, 177);
contentPane.add(scrollPane_1);
textArea_1.setFont(new Font("Monospaced", Font.PLAIN, 15));
scrollPane_1.setViewportView(textArea_1);
JScrollPane scrollPane_2 = new JScrollPane();
scrollPane_2.setBounds(265, 49, 62, 177);
contentPane.add(scrollPane_2);
textArea_2.setFont(new Font("Monospaced", Font.PLAIN, 18));
scrollPane_2.setViewportView(textArea_2);
textArea_2.setBackground(UIManager.getColor("Button.background"));
JButton btnCallTimer = new JButton("Call timer");
btnCallTimer.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
new timer().setVisible(true); }
});
btnCallTimer.setBounds(297, 238, 127, 23);
contentPane.add(btnCallTimer);
guidel界面:

进入中文简体界面:

九 界面模块与计算模块对接
调用了Cal的cal方法,和Create2的create方法被调用。




十 结队过程

十一 结队优点缺点
结队编程优点:
1 两人办事按理说会有加成,效率更高。
2 两个人按理说各自分工,可以减轻压力。
结队编程缺点:
1 一个跳票的队员永远比一个单纯划水的队员可怕,你永远不知道他的马上会是几个小时或是几天,更可怕的是他把自己都忽悠信了。
2 因为对于某些技术细节的不同意见,或者是对于某些问题的理解不同,可能产生分歧,比如读这次作业的题目,我是怎么也不觉得可以做一个微信小程序。
3 不同人的性格未必相同。性格比较急躁的人可能不赞同deadline几小时前赶一下界面模块的。
队员优缺点:
张舒凯:
优点:花的时间比较多。
缺点:人傻,不知道见微知著。脾气暴躁,过于push。编程能力欠佳,功能实现得太慢
葛金星:
优点:脾气温和。性格沉稳。
缺点:想法太多。

浙公网安备 33010602011771号