PTA第二阶段Blog作业
在完成这三次的题目集的过程中,越发觉得我对于基础知识的学习还不够,只是大概能写出一些简单的程序,一旦运用复杂的结构的时候就显得特别力不从心了。而且对于各个知识点的运用也有点知其然而不知其所以然,每次写程序都要先看看别人是怎么写的,然后才会有自己的思路。有的甚至就是在别人的代码上进行加工,在此我深深的总结检讨一下自己。
一、题目集4(7-2)和题目集5(7-4)做题时的感受:
在做(7-2)的时候我想自己独立并按照题目给的类图去写代码,但是在经过n个小时的挣扎之后我决定参考一下别人是怎么写的,并且也抛弃了按照类图写代码的想法,只是分为了两个类,而没有再继续分,说到底还是不清楚各个类和方法之间的调用,而这也使得我在农夫过河的实验中吃尽了苦头。言归正传,我参考网上的代码吸取了其中两个关键点,一个是每个月的最大天数,在此我跟他一样运用了两个数组。
private int[] mon_maxnum = {0,31,29,31,30,31,30,31,31,30,31,30,31}; private int[] mon_minnum = {0,31,28,31,30,31,30,31,31,30,31,30,31};
这样就解决了每月的天数问题,其实这种题上个学期就已经学过,但是当时并没有查重,而且对于C语言的学习有点烦,然后那次的学习机会就失去了,这种方法就只能借鉴别人的了。然后就是查找下n天是哪天,我采用了一天一天遍历过去。
//下n天 public void getNextDay(int n) { for(int i=0;i<n;i++) { day++; if(isLeapYear()) { if(day > mon_maxnum[month]) { day = 1; month++; if(month>12) { month = 1; year++; } } } else { if(day > mon_minnum[month]) { day = 1; month++; if(month>12) { month = 1; year++; } } } } System.out.println(year + "-" + month + "-" + day); }
同理求前n天,和两个日期有多少天也是依葫芦画瓢,这样这道题算是解决了。到了(7-4)的时候,我以为跟之前一样的代码,然后修改一些数据就行了,但是提交之后就悲催了,运行超时。之后我就运用我一开始的思路,按我们正常人算的思路来写。
// 下n天 public void getNextDay(int n) { int n1 =n; int a=0; //System.out.println(n); while(a==0) { if( n > getDayOfMonth(year, month)) { n=( n - getDayOfMonth(year, month))+ day; day = 0; month++; if(month>12) { year++; month=1; } } else { if(day+ n > getDayOfMonth(year, month)) { n=( n - getDayOfMonth(year, month))+ day; day = 0; month++; if(month>12) { year++; month=1; } } else { day = day+n; a=1; } } } System.out.println(year_3 + "-" + month_3 + "-" + day_3 + " next " + n1 + " days is:" + year + "-" + month + "-" + day); }
当然在这其中也碰到了一些问题,就是int类型数的最大时那个测试点没过,又是查又是测才发现是自己的逻辑出现了问题。
n=( n - getDayOfMonth(year, month))+ day;
上面是我修改之后的代码,下面是我修改之前的,
n= n +day-getDayOfMonth(year, month);
我才想起这个先从左到右算,当最大值加上一个正数后会超出int所能承载的最大值,会导致其变为负值,而在改完之后就没有这个问题了。
而这其中我觉得比较关键的找出PTA程序的测试点是一个比较难的,首先得需要弄明白哪部分的代码出现了问题,然后就是为什么会错。而且有时候题目给的输入示例又是正确的,然后其他的错误的测试点,又没有示例给出对比,也不知道输出的是不是正确的数据,这就非常的折磨人。这就需要自己去推算了,有的又根本就没有办法去推算,我觉得这才是最烧脑的。反正我在(7-40的测试的时候弄了好久,首先就是弄明白哪里错了,然后还需要自己再看一遍代码,自己查找错误,也幸好自己能看懂自己写的到底是啥东东,有的人根本就认不出自己写的代码。
二、题目集4(7-3)与题目集5(7-5、7-6)的写后感:
首先我是去看了一下继承的内容,但是并没有看完整,只是大概知道了就开始写代码了,但是在写的过程中又不知该如何继承,看书又觉得自己没错,但是在问过同学之后i才想起自己漏了super这一部分没看,最终是写出来了,但是似乎还是有点知其然而不知其所以然,只知道应该这样写,而且还觉得这有没有其实差别不大。但是在eclipse几次报错提醒之后才明白了子类可以继承父类的方法而不需要重新再写。
而(7-5)题因为有上一次的经验能顺利写出来,就是(7-6)这道题目有点没弄懂该怎么正确写,当然在这之前我是看过视频了,在eclipse上能写出来,但是移到pta就不知道怎么弄了,最后也是在eclipse上将接口和主代码放在一个文件才弄明白要怎么写,说到底就是要加一个
import java.util.*;而不是 import java.util.Arrays;


总的来说这几道题目还是比较简单的。也就(7-5)题按照那个解题报告,我又学习了一下ArrayList类,初步懂得了其中方法的运用,主要还是我看了一下相关的视频,不会跟之前一样显得手足无措,只是按照之前学习C语言的思路来写。接口这部分在这几道题目显得比较简单,还能写出来。
import java.util.Scanner; //import java.util.Arrays; //import java.util.Collections; import java.util.*; public class Main { public static void main(String[] args) { ArrayList<Double> a = new ArrayList<Double>(); Scanner sc = new Scanner(System.in); String s = sc.nextLine(); String [] ss = s.split(" "); double [] data = new double[ss.length]; for(int i=0;i<ss.length;i++) { ss[i] = ss[i].trim(); data[i] = Double.parseDouble(ss[i]); } if(data[0] + 2 * data[1] + 3* data[2] < ss.length - 3) { System.out.println("Wrong Format"); return; } int x1 = (int) data[0]; int x2 = (int) data[1]; int x3 = (int) data[2]; double [] area = new double[x1+x2+x3]; for(int i=0;i<x1;i++) { Circle circle = new Circle(); circle.setRadius(data[3 + i]); // System.out.println(circle.validate()); if(circle.validate() == true) { area[i] = circle.getArea(); } else { System.out.println("Wrong Format"); return; } } for(int i=0;i<x2;i++) { Rectangle rectangle = new Rectangle(); rectangle.setWidth(data[3 + x1+i * 2]); rectangle.setLength(data[4 + x1+i * 2]); // System.out.println(rectangle.validate()); if(rectangle.validate() == true) { area[x1+i] = rectangle.getArea(); } else { System.out.println("Wrong Format"); return; } } for(int i=0;i<x3;i++) { Triangle triangle = new Triangle(); triangle.setSide1(data[3 + x1+2*x2+i * 3]); triangle.setSide2(data[4 + x1+2*x2+i * 3]); triangle.setSide3(data[5 + x1+2*x2 +i * 3]); //System.out.println(data[3 + x1+2*x2+i * 3]); // System.out.println(data[4 + x1+x2+i * 3]); //System.out.println(data[5 + x1+x2+i * 3]); //System.out.println(triangle.validate()); if(triangle.validate() == true) { area[x1+x2+i] = triangle.getArea(); } else { System.out.println("Wrong Format"); return; } } System.out.println("Original area:"); for(int i=0;i<x1+x2+x3;i++) { System.out.printf("%.2f ",area[i]); } double sum = 0; for(int i=0;i<x1+x2+x3;i++) { sum = sum + area[i]; } System.out.printf("\nSum of area:%.2f",sum); for(int i=0;i<x1+x2+x3;i++) { a.add(area[i]); } Collections.sort(a); System.out.println("\nSorted area:"); for(double i:a) { System.out.printf("%.2f ",i); } System.out.printf("\nSum of area:%.2f",sum); } } abstract class Shape { public abstract double getArea() ; public abstract boolean validate() ; //public abstract String toString() ; } class Circle extends Shape { private double radius ; public void setRadius(double radius) { this.radius = radius; } public double getArea() { return Math.PI * Math.pow(radius, 2); } public boolean validate() { if(radius <= 0) { return false; } else { return true; } } } class Rectangle extends Shape { private double width; private double length; public void setWidth(double width) { this.width = width; } public void setLength(double length) { this.length = length; } public double getArea() { return width * length; } public boolean validate() { if(width < 0 || length < 0) { return false; } else { return true; } } } class Triangle extends Shape { private double side1; private double side2; private double side3; public void setSide1(double side1) { this.side1 = side1; } public void setSide2(double side2) { this.side2 = side2; } public void setSide3(double side3) { this.side3 = side3; } public boolean validate() { if(side1 < 0 || side2 < 0 ||side3 < 0 || side1 + side2 <= side3||side3 + side2 <= side1||side1 + side3 <= side2) { return false; } else { return true; } } public double getArea() { double p = (side1 + side2 + side3)/2; return Math.sqrt(p * (p - side1) * (p - side2) * (p - side3)); } }
三、题目集5(7-4)中Java集合框架应用的分析总结:
对于这道题没什么好说的主要还是我自己还没弄懂是什么情况,而且研究网上别人写的代码也没有研究出个所以然来,其实然后就是写这道题的时间太短了,没有充分时间去研究,然后对于集合还是处于比较懵逼的状态,在结束那晚才在图书馆研究代码,在研究一晚上之后发现测试点反而更多的没有通过了,而且在查重方面还高达94%的重复率。现在我痛定思痛,还是觉得应该好好学习一下Java的知识,毕竟Java并不像C语言那样简单。言归正传,这道题的主要的难点其实并不是新的知识点——集合,而是跟之前(7-1 )题水文数据校验及处理 的题目一样关键在于输入数据的切割整理,一旦切割好了,这道题目就基本写出来了,而说到底其实也是正则表达式的运用是一个难点,而这就是下一部分需要总结的。

四、三次题目集正则表达式的总结:
题目集六的正则表达式在经过几次对其的熟悉之后,能很快地写出来,当然也有其比较简单的原因,总之题目集六是比较简单,难的还是在(7-1)和(7-4)这两道题,首先就说一下(7-1)吧,这道题的年份那一部分的判断很难弄懂,主要就是在闰年和平年的判断有点难以想到,最终还是看网上是怎么判断的。
Pattern p = Pattern.compile("((([1-9]{1}|[1-9][0-9]{1}|[1-9][0-9]{2}|[1-9][0-9]{3})/((([13578]|1[02])/([1-9]|[12][0-9]|3[01]))|(([469]|11)/([1-9]|[12][0-9]|30))|(2/([1-9]|[1][0-9]|2[0-8]))))|((([1-9]{0,1}[0-9]{0,1})(0[48]|[2468][048]|[13579][26])|((0[48]|[2468][048]|[3579][26])00))/2/29)) ([02468]|1[02468]|2[02]):00");
其他的话都还是比较简单的。还有比较难的就是数据的切割,需要好好想一想应该怎么去切割数据,并且应该怎么去判断和应用。而且对于数据用正则表达式在一些简单的应用并不会太难,就是对一些动态数据的处理有些难,还有就是一些转义字符,有些根本就不知道应该怎么去表示,而这就是(7-4)题的难点了,对于注释符号不知道应该怎么写,应该怎么转义。再有就是老是写到一半就忘了,思路混了。
//7-1 StringBuilder s = new StringBuilder(input.nextLine()); String s1 = input.nextLine(); String s2 = "exit"; int n = 0; int n1 = 0; while(s1.equals(s2) == false) { s.append('\n'+s1);//append追加字符数组到 s1 = input.nextLine(); n++; } //7-4 String s2 = "exit"; while(true) { String s1 = input.nextLine(); if(s1.equals(s2) == true) break; if(s1.matches("(.*)////(.*)")) {//将注释和内容分割开 String b[]=s1.split("////"); s.append(b[0]+" "); } else { s.append(s1+" "); } }
我在写7-4的时候以为可以跟7-1一样,结果就错了,因为代码的注释可以在不同位置,而大括号的位置也因人习惯而异,所以我就特别迷糊了,看着别人的代码觉得理所当然可是到了自己的时候却又没有任何思路,这就有点悲催了,最终也导致查重率过高。且经过这次的练习让我印象深刻,在没彻底弄懂应该怎么写之前不要修改别人的代码,要不然就会丢人现眼。
五‘其它题目的总结:
其他的题目都不是很难,而这些也只是学习一下就会了,比如插入排序,而之前我只学了冒泡排序和选择排序。然后就是一些之前做过的题目,都比较简单。

浙公网安备 33010602011771号