结对编程(Java实现)
? ? ? ? ? ?https://github.com/Importlif/ARi
计算结果函数 ? String cuclate(String str) { while(str.indexOf("÷")!=-1||str.indexOf("×")!=-1) { int pos; for(pos=0;;pos++) { if(str.charAt(pos)==‘ב||str.charAt(pos)==‘÷‘) { break; } } int mark; String leftStr=""; mark = pos - 1; while (mark >= 0 && (str.charAt(mark) != ‘+‘ && str.charAt(mark) != ‘-‘ && str.charAt(mark) != ‘ב && str.charAt(mark) != ‘÷‘)) { mark--; } if (mark > 0) { leftStr = str.substring(0,mark+1); } mark++; String sub=str.substring(mark,pos); long i=Long.parseLong(sub.substring(0,sub.indexOf("’"))); long i1=Long.parseLong(sub.substring(sub.indexOf("’")+1,sub.indexOf("/"))); long i2=Long.parseLong(sub.substring(sub.indexOf("/")+1)); String rightStr=""; mark = pos + 1; while (mark < str.length() && (str.charAt(mark) != ‘+‘ && str.charAt(mark) != ‘-‘ && str.charAt(mark) != ‘ב && str.charAt(mark) != ‘÷‘)) { mark++; } mark--; if (mark < str.length()-1) { rightStr = str.substring(mark+1); } String sub1=str.substring(pos+1,mark+1); long j=Long.parseLong(sub1.substring(0,sub1.indexOf("’"))); long j1=Long.parseLong(sub1.substring(sub1.indexOf("’")+1,sub1.indexOf("/"))); long j2=Long.parseLong(sub1.substring(sub1.indexOf("/")+1)); if (str.charAt(pos)==‘ב) { long result[]=multiply(new long[] {i,i1,i2},new long[] {j,j1,j2}); str=leftStr+Long.toString(result[0])+"’"+Long.toString(result[1])+"/"+Long.toString(result[2])+rightStr; } else { long result[]=devided(new long[] {i,j2}); str=leftStr+Long.toString(result[0])+"’"+Long.toString(result[1])+"/"+Long.toString(result[2])+rightStr; } } while(str.indexOf("+")!=-1||str.indexOf("-")!=-1) { int pos; for(pos=0;;pos++) { if(str.charAt(pos)==‘+‘||str.charAt(pos)==‘-‘) { break; } } int mark; String leftStr=""; mark = pos - 1; while (mark >= 0 && (str.charAt(mark) != ‘+‘ && str.charAt(mark) != ‘-‘ && str.charAt(mark) != ‘ב && str.charAt(mark) != ‘÷‘)) { mark--; } if (mark > 0) { leftStr = str.substring(0,sub.indexOf("/"))); long i2=Long.parseLong(sub.substring(sub.indexOf("/")+1)); String rightStr=""; mark = pos + 1; while (mark <str.length() && (str.charAt(mark) != ‘+‘ && str.charAt(mark) != ‘-‘ && str.charAt(mark) != ‘ב && str.charAt(mark) != ‘÷‘)) { mark++; } mark--; if (mark < str.length()-1) { rightStr = str.substring(mark+1); } String sub1=str.substring(pos+1,sub1.indexOf("/"))); long j2=Long.parseLong(sub1.substring(sub1.indexOf("/")+1)); if (str.charAt(pos)==‘+‘) { long result[]=add(new long[] {i,j2}); str=leftStr+Long.toString(result[0])+"’"+Long.toString(result[1])+"/"+Long.toString(result[2])+rightStr; } else { long result[]=minus(new long[] {i,j2}); if(result[0]<0||result[1]<0) { return "false"; } str=leftStr+Long.toString(result[0])+"’"+Long.toString(result[1])+"/"+Long.toString(result[2])+rightStr; } } return str; } public String match(String str)// { Stack<Integer> stack=new Stack<Integer>(); for(int i=0;i<str.length();i++) { if(str.charAt(i)==‘(‘) { stack.push(i); } if(str.charAt(i)==‘)‘) { int tag=(int) stack.peek(); stack.pop(); String check; check=cuclate(str.substring(tag+1,i)); if(check.equals("false")) { return "false"; } str=str.substring(0,tag)+cuclate(str.substring(tag+1,i))+str.substring(i+1);//先算括号里面的,从而去掉括号 i=0; } } if(str.length()>0 &&str.indexOf("(")==-1){ str=cuclate(str);//没括号的话直接算 } else str = match(str); return str; } 在match函数中,通过使用栈的方法进行括号匹配,实现有括号先算括号,把遇到的左括号的位置压入栈中,当遇到右括号时,取出栈顶元素,将左右括号之间的式子调用cuclate函数进行计算并返回结果。在cuclate函数中,按照四则运算法则进行计算,先乘除,后加减,计算完成后返回结果。同时在cuclate中遇到减法时检测计算结果,如果出现负数则返回false,并舍弃该题目重新生成。 ?题目生成函数 public String creator(long r) { //随机决定生成带分数或分数或整数 int decide = (int)(Math.random() * 3) + 1; String str ; switch(decide){//真分数二又八分之三表示为2’3/8。 case 1 : long sumc = (long)(Math.random() * r-1) + 1; long fenmuc = (long)(Math.random() * r-1) + 2; long fenzic = (long)(Math.random() * fenmuc-1) + 1; while(Euclid(fenmuc,fenzic) != 1) {//生成不可约的分数 fenmuc = (long)(Math.random() * r-1) + 2; fenzic = (long)(Math.random() * fenmuc-1) + 1; } str = String.valueOf(sumc)+"’"+String.valueOf(fenzic)+"/"+String.valueOf(fenmuc);break; case 2 : long fenmud = (long)(Math.random() * r-1) + 2; long fenzid = (long)(Math.random() * fenmud-1) + 1; while(Euclid(fenmud,fenzid) != 1) {//生成不可约的分数 fenmud = (long)(Math.random() * r-1) + 2; fenzid = (long)(Math.random() * fenmud-1) + 1; } str = String.valueOf(fenzid)+"/"+String.valueOf(fenmud);break; default: long sum = (long)(Math.random() * r-1) + 1; str = String.valueOf(sum);break; }//生成第一个数str int sign_num = (int)(Math.random() * 3) + 1;//随机决定总共生成多少个数 while(sign_num != 0) { //生成后面的式子 int decide2 = (int)(Math.random() * 3) + 1;//随机决定生成带分数或分数或整数 String str2 ; switch(decide2){//真分数二又八分之三表示为2’3/8。 case 1 : long sumc2 = (long)(Math.random() * r-1) + 1; long fenmuc2 = (long)(Math.random() * r-1) + 2; long fenzic2 = (long)(Math.random() * fenmuc2-1) + 1; while(Euclid(fenmuc2,fenzic2) != 1) {//生成不可约的分数 fenmuc2 = (long)(Math.random() * r-1) + 2; fenzic2 = (long)(Math.random() * fenmuc2-1) + 1; } str2 = String.valueOf(sumc2)+"’"+String.valueOf(fenzic2)+"/"+String.valueOf(fenmuc2);break; case 2 : long fenmu2 = (long)(Math.random() * r-1) + 2; long fenzi2 = (long)(Math.random() * fenmu2-1) + 1; while(Euclid(fenmu2,fenzi2) != 1) {//生成不可约的分数 fenmu2 = (long)(Math.random() * r-1) + 2; fenzi2 = (long)(Math.random() * fenmu2-1) + 1; } str2 = String.valueOf(fenzi2)+"/"+String.valueOf(fenmu2);break; default: long sum2 = (long)(Math.random() * r-1) + 1; str2 = String.valueOf(sum2);break; } int sign_flag = (int)(Math.random() * 4) + 1; switch(sign_flag){//真分数二又八分之三表示为2’3/8。 case 1 : str = str +"+"+str2;break; case 2 : str = str +"-"+str2;break; case 3 : str = str +"×"+str2;break; default : str = str +"÷"+str2; int bracket = (int)(Math.random() * 2) + 1; if(bracket == 1 && sign_num != 1 && ( str.indexOf("-")!= -1 ||str.indexOf("+")!= -1)) str = "("+str+")"; } sign_num--; } return str; } ? 生成题目思路: 1.先随机生成一个数:用random()方法,随机决定生成一个数(1或2或3),如果是1,则生成一个带分数,如果是2,则生成一个分数;如果是3,则生成一个整数。作为一个字符串。假如生成“5/8”。 2.再随机生成一个数:用random()方法,随机决定生成一个数(1或2或3),如果是1,则生成一个带分数,如果是2,则生成一个分数;如果是3,则生成一个整数。作为一个字符串。假如生成“9”。 3.再随机生成一个符号将上述两个数拼接起来成为一条式子:用random()方法,随机决定生成一个数(1或2或3或4),如果是1,则生成+,如果是2,则生成-;如果是3,则生成×,如果是4,则生成÷。拼接起来作为一个字符串。假如符号是×,生成的是 5/8×9 4.随机决定是否生成括号,假如生成(5/8×9) 5.随机决定是否重复上面1-4,直到结束。从而形成一条式子。
运行演示: 出题: ? 对答案: ? ? 用例1:测试对答案功能:题目和答案都为空 ? ? ? ? 用例2:生成一道题 ? ? ? 用例3:测试对答案功能:题目全是带分数形式,答案正确的9道题。 ? ? 用例4:测试对答案功能:题目全是带分数形式,除了第五第九题,其余答案正确的9道题。 ? ? 用例5:测试对答案功能:题目全是带分数形式,部分答案能化简但没化简(算作错误),其余答案正确的一万道题。 ? ? ? ?说明我们出题功能里实现的输出是符合需求的,即“真分数在输入输出时采用如下格式,真分数五分之三表示为3/5,真分数二又八分之三表示为2’3/8。”并且具有计算10000道题的能力。 用例6:生成题目全是自然数和真分数,答案正确的10道题,测试出题功能 ? 可见我们的出题功能是符合需求的,即“真分数在输入输出时采用如下格式,真分数五分之三表示为3/5,真分数二又八分之三表示为2’3/8。”而且如第九题,能正确生成括号。 用例7:测试对答案功能:测试题目全是自然数和真分数时的对答案功能,其中答案只有前五题5个正确答案, 后五题无答案 ? 用例8:测试对答案功能:测试题目全是自然数和真分数时的对答案功能 ? ? ? ? ?题目是自然数和真分数的情况下也能正确检测答案正确性。 用例9:生成题目全是自然数和真分数,答案正确的10000道题,测试大量出题功能 点击出题 ? ? ? 从开始出题提示框点击确定开始到出题完成用时1秒多。能正确生成括号。无重复题。 题目的数字不超过给定参数20。 ? ?用例10:用上述生成的10000道题,测试对答案功能 ? 判断10000题用时和出题10000道差不多,用了1秒多的时间。 7.项目小结 通过这次的结对编程,使我们对编程有了新的认识,在双人模式下,一个人一边写代码,一边说思路,另一个人在旁听,旁听的同学通过边听边看,能发现打代码同学可能出现的一些bug进而及时修正,减少错误可能发生的概率,提升了工作效率。同时在结对编程的过程中,对于同一个问题可能会有不同的解决办法,通过讨论,我们能得出相对较优的算法,进而提升程序的效率。同时由于常用语言的不同,在转化方面我们更要去认真了解不同语言实现同一个函数功能之间的差异。 (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |