一,前言
题集四主要考察了arraylist数组的运用,面向对象的封装性,运用数组高效率去重以及运用数组的一些自带方法解决问题,题量较小,除了7-1之外,其它题目难度较低。除此之外,7-6要求我们自主学习Scanner类中nextLine()等方法、String类中split()等方法、Integer类中parseInt()等方法的用法,了解LocalDate类中of()、isAfter()、isBefore()、until()等方法的使用规则,了解ChronoUnit类中DAYS、WEEKS、MONTHS等单位的用法。7-1是菜单计价程序的开始,但是我没做完,时间有点不够。做这次题集我花了很多时间。
题集五主要考察了正则表达式的简单运用,聚合关系,题目难点在于日期类设计聚合一,日期类设计聚合二,题量较小,难度较低,是这两次作业里面比较轻松的了。做这次题集没有花费我多长时间。
题集六只有一个题目,就是菜单计价程序-4,这个题目我没有写出来,我只写了700多行代码,只拿了一点点分,我感觉最难的就是输入数据的处理和输出结果很难搞,太多异常处理,没有一点头绪,做的时候又静不下心来,导致浪费了很多时间没有做出来。
二,设计与分析
题集四7-1菜单计价程序
题目要求写一个菜单计价程序,这题的细节很多,所以难度偏大,在对用户正常点菜的需求下,还需要满足代点菜的特殊要求。除此之外,还有一些输入异常的错误需要进行判断,时间段的限制与折扣。写好这题需要正确的辨别各种类之间的关系以及输入异常的先后关系,以及对输入的正常数据进行处理。题目已经给了一些类的设计模板,按照题目已给的类再设计其他的类。在我的设计代码中只写了Dish,Menu,Record,Order,Table以及Main类。我觉得这一题的要注意的点在于代点菜总价钱的计算设计,因为带点菜的价格计算在当前这一桌,总价不一定等于当前桌上的菜的价格之和。还有就是计算折扣,这里可以用Calendar类里面的方法去求某天是星期几,题目并没有限制,这是我所设计的代码逆生成的类图。
题集四7-4
单词统计与排序
从键盘录入一段英文文本(句子之间的标点符号只包括“,”或“.”,单词之间、单词与标点之间都以" "分割。
要求:按照每个单词的长度由高到低输出各个单词(重复单词只输出一次),如果单词长度相同,则按照单词的首字母顺序(不区分大小写,首字母相同的比较第二个字母,以此类推)升序输出。
做这道题时我一开始尝试用split方法将英文文本中的“,”,“.”,“ ”都去掉,返回一个字符串数组,再用冒泡排序的方法去做,但是我当时不知道怎么去删除重复的字符串数组,尝试了几种方法都没有用,然后又想用arraylist中的方法中有删除的简单方法,结果自己又不会怎样将String类型的数组转换成Array List类型的数组,属实是做不了了,之后就用了另一种方法去做,具体代码如下:
1 import java.util.Scanner; 2 import java.util.ArrayList; 3 public class Main { 4 public static void main(String[] args){ 5 Scanner input = new Scanner(System.in); 6 String str = input.nextLine(); 7 ArrayList <String> list= new ArrayList<>(); 8 String segment=""; 9 int i=0,j=0,k=0; 10 for(i=0;i<str.length();i++){ 11 if(str.charAt(i)==' '){ 12 list.add(segment); 13 segment="";//每次添加完,都要归零 14 } 15 else if(str.charAt(i)=='.'||str.charAt(i)==','){ 16 list.add(segment); 17 segment=""; 18 i++;//向后走一步,因为有空格 19 } 20 else{ 21 segment=segment+str.charAt(i); 22 } 23 } 24 //删除重复元素 25 for(i=0;i<list.size()-1;i++){ 26 for(j=i+1;j<list.size();j++){ 27 if(list.get(i).equals(list.get(j))){ 28 list.remove(j); 29 j--;//一删一减,j不变 30 } 31 } 32 } 33 //按照长度冒泡排序 34 for(i=0;i<list.size()-1;i++){ 35 for(j=0;j<list.size()-1-i;j++){ 36 if(list.get(j).length()<list.get(j+1).length()){ 37 segment=list.get(j); 38 list.set(j,list.get(j+1)); 39 list.set(j+1,segment); 40 } 41 else if(list.get(j).length()==list.get(j+1).length()){ 42 if(list.get(j).compareToIgnoreCase(list.get(j+1))>0) {//不区分大小写 43 segment=list.get(j); 44 list.set(j,list.get(j+1)); 45 list.set(j+1,segment); 46 } 47 48 } 49 } 50 51 } 52 for(i=0;i<list.size();i++){ 53 System.out.println(list.get(i)); 54 } 55 } 56 }View Code
这段代码就是先处理掉文本中的非英文字符,在删除重复元素,最后在排序。去除非英文字符时,采用的是一个一个英文字符添加到单词的临时储存变量中,直到碰见“,”,“.”,“ ”,停止,才将单词加入数组,之后再清空临时变量。之后就是去重和排序操作了,非常的简单粗暴。由于ArrayList数组的删除,添加等操作都较为方便,代码几乎没啥难度。
题集五7-5日期问题面向对象设计(聚合一)
1.设计如下几个类:DateUtil、Year、Month、Day,其中年、月、日的取值范围依然为:year∈[1900,2050] ,month∈[1,12] ,day∈[1,31] 。题目设计要求DateUtil聚合于Day,Day聚合于Month,Month聚合于Year。在做这个题目时,主要的难度便是设计类与类之间的聚合关系,具体的日期算法之前便已经设计过,这里可以直接拿过来用,稍作修改即可。编写代码实现功能时通过DateUtil中的Day类型的属性去调用Day类中的方法以及Month类型的属性,再用Month类型的属性去调用Month中的方法以及Year类型的属性,再用Year类型的属性去调用调用Year的方法。我开始做这个题目有一点让我迷惑的点是DateUtil类,Day类,Month类,Year的类的有参构造方法,刚开始看类图的时候还没反应过来,不知道这些方法传这些参数是为啥,之后整个代码快写完了才想明白,这些构造方法是连着写的。这个题目的算法已经设计过了,由于类中的属性都是私有的,将算法中的直接引用改为属性的get方法即可。还有一个问题就是判断输入日期数据是否合法没有写好,没有判断输入的月份是否大于12或小于1,因为判断日期输入是否正确是要用每月最大天数数组的,导致数组越界异常。具体代码以及sourceMonitor生成图如下:
1 import java.util.Scanner; 2 3 public class Main { 4 public static void main(String[] args) { 5 Scanner input = new Scanner(System.in); 6 int year = 0; 7 int month = 0; 8 int day = 0; 9 10 int choice = input.nextInt(); 11 12 if (choice == 1) { // test getNextNDays method 13 int m = 0; 14 year = Integer.parseInt(input.next());//转化输入数据 15 month = Integer.parseInt(input.next()); 16 day = Integer.parseInt(input.next()); 17 18 DateUtil date = new DateUtil(year,month,day);//创建对象 19 20 21 if (!date.checkInputValidity()) { 22 System.out.println("Wrong Format"); 23 System.exit(0); 24 } 25 26 m = input.nextInt(); 27 28 if (m < 0) { 29 System.out.println("Wrong Format"); 30 System.exit(0); 31 } 32 33 System.out.println(date.getNextNDays(m).showDate()); 34 } else if (choice == 2) { // test getPreviousNDays method 35 int n = 0; 36 year = Integer.parseInt(input.next());//转化输入数据 37 month = Integer.parseInt(input.next()); 38 day = Integer.parseInt(input.next()); 39 40 DateUtil date = new DateUtil(year,month,day);//创建对象 41 42 if (!date.checkInputValidity()) { 43 System.out.println("Wrong Format"); 44 System.exit(0); 45 } 46 47 n = input.nextInt(); 48 49 if (n < 0) { 50 System.out.println("Wrong Format"); 51 System.exit(0); 52 } 53 54 System.out.println(date.getPreviousNDays(n).showDate()); 55 } else if (choice == 3) { //test getDaysofDates method 56 year = Integer.parseInt(input.next());//转化输入数据 57 month = Integer.parseInt(input.next()); 58 day = Integer.parseInt(input.next()); 59 60 int anotherYear = Integer.parseInt(input.next()); 61 int anotherMonth = Integer.parseInt(input.next()); 62 int anotherDay = Integer.parseInt(input.next()); 63 64 DateUtil fromDate = new DateUtil(year,month,day);//创建对象 65 66 DateUtil toDate = new DateUtil(anotherYear,anotherMonth,anotherDay);//创建对象 67 if (fromDate.checkInputValidity() && toDate.checkInputValidity()) { 68 System.out.println(fromDate.getDaysofDates(toDate)); 69 } else { 70 System.out.println("Wrong Format"); 71 System.exit(0); 72 } 73 } 74 else{ 75 System.out.println("Wrong Format"); 76 System.exit(0); 77 } 78 } 79 } 80 81 82 class DateUtil { 83 private Day day;//日期对象 84 85 86 public DateUtil() {//无参构造 87 88 } 89 public DateUtil(int y,int m,int d) {//有参构造 90 this.day = new Day(y,m,d); 91 92 } 93 94 public Day getDay() {//day的get 95 return day; 96 } 97 98 public void setDay(Day day) {//day的set 99 this.day = day; 100 } 101 102 public String showDate(){//输出形式 103 String str=day.getMonth().getYear().getValue()+"-"+day.getMonth().getValue()+"-"+day.getValue(); 104 return str; 105 } 106 public boolean checkInputValidity(){//检查输入日期是否正确 107 boolean result=false; 108 if(day.validate()&&day.getMonth().validate()&&day.getMonth().getYear().validate()) 109 result=true; 110 return result; 111 } 112 public boolean compareDates(DateUtil date){//比较两日期大小 113 boolean result=false; 114 if(this.getDay().getMonth().getYear().getValue()>date.getDay().getMonth().getYear().getValue()) 115 result=true; 116 else if(this.getDay().getMonth().getYear().getValue()==date.getDay().getMonth().getYear().getValue()&&this.getDay().getMonth().getValue()>date.getDay().getMonth().getValue()) 117 result=true; 118 else if(this.getDay().getMonth().getYear().getValue()==date.getDay().getMonth().getYear().getValue()&&this.getDay().getMonth().getValue()==date.getDay().getMonth().getValue()&&this.getDay().getValue()>date.getDay().getValue()) 119 result=true; 120 return result; 121 } 122 public boolean equalTwoDates(DateUtil date){//检查两日期是否相等 123 boolean result=true; 124 if(this.getDay().getMonth().getYear().getValue()!=date.getDay().getMonth().getYear().getValue()) 125 result=false; 126 else if(this.getDay().getMonth().getValue()!=date.getDay().getMonth().getValue()) 127 result=false; 128 else if(this.getDay().getValue()!=date.getDay().getValue()) 129 result=false; 130 return result; 131 } 132 public DateUtil getNextNDays(int n){//求下N天 133 int[] mon_maxnum= {31,28,31,30,31,30,31,31,30,31,30,31}; 134 while(n>365){//大于一年时 135 if(this.getDay().getMonth().getValue()<=2){//判断该年是否为闰年 136 if(this.getDay().getMonth().getYear().isLeapYear()){ 137 n=n-366; 138 this.getDay().getMonth().getYear().yearIncrement(); 139 } 140 else{ 141 n=n-365; 142 this.getDay().getMonth().getYear().yearIncrement(); 143 } 144 } 145 else if(this.getDay().getMonth().getValue()>2){ 146 this.getDay().getMonth().getYear().yearIncrement();//判断下一年是否为闰年 147 if(this.getDay().getMonth().getYear().isLeapYear()){ 148 n=n-366; 149 } 150 else{ 151 n=n-365; 152 } 153 } 154 } 155 for(int i=0;i<n;i++){//小于一年时 156 this.getDay().dayIncrement(); 157 if(this.getDay().getMonth().getYear().isLeapYear()){//判断该年是否为闰年 158 mon_maxnum[1]=29; 159 } 160 else 161 mon_maxnum[1]=28; 162 if(this.getDay().getValue()>mon_maxnum[this.getDay().getMonth().getValue()-1]){ 163 this.getDay().getMonth().monthIncrement();//月份进位 164 this.getDay().reseMin(); 165 if(this.getDay().getMonth().getValue()>12){ 166 this.getDay().getMonth().getYear().yearIncrement();//年份进位 167 this.getDay().getMonth().reseMin(); 168 } 169 } 170 } 171 return this; 172 } 173 174 public DateUtil getPreviousNDays(int n){//求前N天 175 int[] mon_maxnum= {31,28,31,30,31,30,31,31,30,31,30,31}; 176 while(n>365){//大于一年时 177 if(this.getDay().getMonth().getValue()>2){ 178 if(this.getDay().getMonth().getYear().isLeapYear()){//判断该年是否为闰年 179 this.getDay().getMonth().getYear().yearReduction(); 180 n=n-366; 181 } 182 else{ 183 this.getDay().getMonth().getYear().yearReduction(); 184 n=n-365; 185 } 186 } 187 else if(this.getDay().getMonth().getValue()<=2){ 188 this.getDay().getMonth().getYear().yearReduction();//判断前一年年是否为闰年 189 if(this.getDay().getMonth().getYear().isLeapYear()){ 190 n=n-366; 191 } 192 else{ 193 n=n-365; 194 } 195 } 196 } 197 for(int i=0;i<n;i++){//小于一年时 198 this.getDay().dayReduction(); 199 if(this.getDay().getValue()<=0){//判断该年是否为闰年 200 if(this.getDay().getMonth().getYear().isLeapYear()){ 201 mon_maxnum[1]=29; 202 } 203 else 204 mon_maxnum[1]=28; 205 this.getDay().getMonth().monthReduction();; 206 if(this.getDay().getMonth().getValue()<=0){//往后退一年 207 this.getDay().getMonth().getYear().yearReduction(); 208 this.getDay().getMonth().reseMax(); 209 } 210 this.getDay().reseMax(); 211 } 212 } 213 return this; 214 } 215 public int getDaysofDates(DateUtil date){//求两日期之间的天数 216 int gap=0; 217 int[] mon_maxnum= {31,28,31,30,31,30,31,31,30,31,30,31}; 218 if(this.compareDates(date)){//第一个日期大于第二个,求的方法与求前n天大致一样 219 while(this.getDay().getMonth().getYear().getValue()-date.getDay().getMonth().getYear().getValue()>=2){//当两个日期相差大于两年时,先减至两年一下再算 220 if(this.getDay().getMonth().getValue()>2){ 221 if(this.getDay().getMonth().getYear().isLeapYear()){//判断该年是否为闰年 222 gap+=366; 223 } 224 else 225 gap+=365; 226 this.getDay().getMonth().getYear().yearReduction(); 227 } 228 if(this.getDay().getMonth().getValue()<=2){ 229 this.getDay().getMonth().getYear().yearReduction();//判断前一年是否为闰年 230 if(this.getDay().getMonth().getYear().isLeapYear()){ 231 gap+=366; 232 } 233 else 234 gap+=365; 235 } 236 } 237 while(true){ 238 if(this.equalTwoDates(date)){ 239 break; 240 } 241 gap++; 242 this.getDay().dayReduction(); 243 if(this.getDay().getValue()<=0){ 244 this.getDay().getMonth().monthReduction(); 245 if(this.getDay().getMonth().getValue()<=0){ 246 this.getDay().getMonth().getYear().yearReduction(); 247 this.getDay().getMonth().reseMax(); 248 } 249 if(this.getDay().getMonth().getYear().isLeapYear()){ 250 mon_maxnum[1]=29; 251 } 252 else 253 mon_maxnum[1]=28; 254 this.getDay().reseMax(); 255 } 256 } 257 } 258 else{//第一个日期小于第二个,求的方法与求后n天大致一样 259 while(date.getDay().getMonth().getYear().getValue()-this.getDay().getMonth().getYear().getValue()>=2){//当两个日期相差大于两年时,先减至两年一下再算 260 if(this.getDay().getMonth().getValue()>2){ 261 this.getDay().getMonth().getYear().yearIncrement();//判断后一年是否为闰年 262 if(this.getDay().getMonth().getYear().isLeapYear()){ 263 gap+=366; 264 } 265 else 266 gap+=365; 267 } 268 if(this.getDay().getMonth().getValue()<=2){ 269 if(this.getDay().getMonth().getYear().isLeapYear()){//判断该年是否为闰年 270 gap+=366; 271 } 272 else 273 gap+=365; 274 this.getDay().getMonth().getYear().yearIncrement(); 275 } 276 277 } 278 while(true){ 279 if(this.equalTwoDates(date)){ 280 break; 281 } 282 gap++; 283 this.getDay().dayIncrement(); 284 if(this.getDay().getMonth().getYear().isLeapYear()){ 285 mon_maxnum[1]=29; 286 } 287 else 288 mon_maxnum[1]=28; 289 if(this.getDay().getValue()>mon_maxnum[this.getDay().getMonth().getValue()-1]){ 290 this.getDay().getMonth().monthIncrement(); 291 this.getDay().reseMin(); 292 if(this.getDay().getMonth().getValue()>12){ 293 this.getDay().getMonth().getYear().yearIncrement(); 294 this.getDay().getMonth().reseMin(); 295 } 296 297 } 298 } 299 } 300 return gap; 301 } 302 } 303 304 305 class Day { 306 private int value;//日期 307 private Month month;//月份对象 308 private int[] mon_maxnum= {31,28,31,30,31,30,31,31,30,31,30,31};//每月最大天数 309 310 public Day() {//无参构造 311 312 } 313 public Day(int yearValue,int monthValue,int dayValue) {//有参构造 314 this.value=dayValue; 315 this.month=new Month(yearValue,monthValue); 316 317 } 318 public int getValue() {//Value的get 319 return value; 320 } 321 public void setValue(int value) {//value的set 322 this.value = value; 323 } 324 public Month getMonth() {//month的get 325 return month; 326 } 327 public void setMonth(Month month) {//month的set 328 this.month = month; 329 } 330 public void reseMin() {//日期复位 331 this.value=1; 332 } 333 public void reseMax() {//日期改为最大值 334 if(this.month.getYear().isLeapYear()) { 335 mon_maxnum[1]=29; 336 }else 337 mon_maxnum[1]=28; 338 this.value=mon_maxnum[month.getValue()-1]; 339 } 340 public boolean validate() {//检查日期是否合法 341 boolean result=false; 342 if(month.getValue()==2&&month.getYear().isLeapYear()) { 343 if(this.value<=29&&this.value>=1) { 344 result=true; 345 } 346 } 347 else { 348 if(month.getValue()<=0||month.getValue()>12) { 349 result=false; 350 } 351 else if(this.value<=mon_maxnum[month.getValue()-1]&&this.value>=1) { 352 result=true; 353 } 354 } 355 return result; 356 } 357 public void dayIncrement() {//日期加一天 358 this.value=this.value+1; 359 } 360 public void dayReduction() {//日期减一天 361 this.value=this.value-1; 362 } 363 } 364 365 class Month { 366 private int value;//月份 367 private Year year;//年的对象 368 369 public Month() { //无参构造 370 371 } 372 public Month(int yearValue,int monthValue) {//有参构造 373 this.value=monthValue; 374 this.year=new Year(yearValue); 375 } 376 public int getValue() {//value的get 377 return value; 378 } 379 public void setValue(int value) {//value的set 380 this.value = value; 381 } 382 public Year getYear() {//year对象的get 383 return year; 384 } 385 public void setYear(Year year) {//year的对象set 386 this.year = year; 387 } 388 public void reseMin() {//月份复位 389 this.value=1; 390 } 391 public void reseMax() {//月份设置为最大 392 this.value=12; 393 } 394 public boolean validate() {//检查月份是否正确 395 boolean result=false; 396 if(this.value>=1&&this.value<=12) { 397 result=true; 398 } 399 return result; 400 } 401 public void monthIncrement() {//月份加一 402 this.value=this.value+1; 403 } 404 public void monthReduction() {//月份减一 405 this.value=this.value-1; 406 } 407 408 } 409 410 411 class Year { 412 private int value;//年份 413 414 415 public Year() {//无参构造 416 417 } 418 public Year(int value) {//有参构造 419 this.value=value; 420 } 421 public int getValue() {//value的get 422 return value; 423 } 424 425 public void setValue(int value) {//value的set 426 this.value = value; 427 } 428 public boolean isLeapYear(){//闰年判断 429 boolean result=false; 430 if((value%4==0&&value%100!=0)||value%400==0) 431 result=true; 432 return result; 433 } 434 public boolean validate() {//年份合法判断 435 boolean result=false; 436 if(value<=2050&&value>=1900) { 437 result=true; 438 } 439 return result; 440 } 441 public void yearIncrement() {//年份加一 442 this.value=this.value+1; 443 } 444 public void yearReduction() {//年份减一 445 this.value=this.value-1; 446 } 447 448 }View Code
题集五7-6日期问题面向对象设计(聚合二)
7-6与7-5代码大致相同,也要求改为聚合关系,只不过是DateUtil聚合Day,Month,Year这三个类。根据类图,DateUtil拥有这三个类的类型的属性,可以直接调用通过这三个属性调用这些类中的方法,然后在DateUtil中完成各种对日期的操作,我感觉这道题要比7-5简单一些,从类图上看这个7-6类图7-5类图少了一些东西,比如并没有让我i们设计判断输入天数是否正确的方法,测的时候也没有测试点检测,原因可能是每个月的最大天数数组在DateUtil中定义成了私有属性,类图中也没有这个数组的get方法,所以就没有考虑。具体代码以及sourceMonitor生成图如下:
1 import java.util.Scanner; 2 3 public class Main { 4 public static void main(String[] args) { 5 Scanner input = new Scanner(System.in); 6 int year = 0; 7 int month = 0; 8 int day = 0; 9 10 int choice = input.nextInt(); 11 12 if (choice == 1) { // test getNextNDays method 13 int m = 0; 14 year = Integer.parseInt(input.next()); 15 month = Integer.parseInt(input.next()); 16 day = Integer.parseInt(input.next()); 17 18 DateUtil date = new DateUtil(year, month, day); 19 20 if (!date.checkInputValidity()) { 21 System.out.println("Wrong Format"); 22 System.exit(0); 23 } 24 25 m = input.nextInt(); 26 27 if (m < 0) { 28 System.out.println("Wrong Format"); 29 System.exit(0); 30 } 31 32 System.out.print(date.getYear().getValue() + "-" + date.getMonth().getValue() + "-" + date.getDay().getValue() + " next " + m + " days is:"); 33 System.out.println(date.getNextNDays(m).showDate()); 34 } else if (choice == 2) { // test getPreviousNDays method 35 int n = 0; 36 year = Integer.parseInt(input.next()); 37 month = Integer.parseInt(input.next()); 38 day = Integer.parseInt(input.next()); 39 40 DateUtil date = new DateUtil(year, month, day); 41 42 if (!date.checkInputValidity()) { 43 System.out.println("Wrong Format"); 44 System.exit(0); 45 } 46 47 n = input.nextInt(); 48 49 if (n < 0) { 50 System.out.println("Wrong Format"); 51 System.exit(0); 52 } 53 54 System.out.print( 55 date.getYear().getValue() + "-" + date.getMonth().getValue() + "-" + date.getDay().getValue() + " previous " + n + " days is:"); 56 System.out.println(date.getPreviousNDays(n).showDate()); 57 } else if (choice == 3) { //test getDaysofDates method 58 year = Integer.parseInt(input.next()); 59 month = Integer.parseInt(input.next()); 60 day = Integer.parseInt(input.next()); 61 62 int anotherYear = Integer.parseInt(input.next()); 63 int anotherMonth = Integer.parseInt(input.next()); 64 int anotherDay = Integer.parseInt(input.next()); 65 66 DateUtil fromDate = new DateUtil(year, month, day); 67 DateUtil toDate = new DateUtil(anotherYear, anotherMonth, anotherDay); 68 69 if (fromDate.checkInputValidity() && toDate.checkInputValidity()) { 70 System.out.println("The days between " + fromDate.showDate() + 71 " and " + toDate.showDate() + " are:" 72 + fromDate.getDaysofDates(toDate)); 73 } else { 74 System.out.println("Wrong Format"); 75 System.exit(0); 76 } 77 } 78 else{ 79 System.out.println("Wrong Format"); 80 System.exit(0); 81 } 82 } 83 } 84 85 86 class DateUtil { 87 private Day day;////创建对象 88 private Month month; 89 private Year year; 90 private int[] mon_maxnum= {31,28,31,30,31,30,31,31,30,31,30,31}; 91 92 public DateUtil() {//无参构造 93 94 } 95 public DateUtil(int y,int m,int d) {//有参构造 96 this.day=new Day(d); 97 this.month=new Month(m); 98 this.year=new Year(y); 99 } 100 public Day getDay() { 101 return day; 102 } 103 public void setDay(Day day) { 104 this.day = day; 105 } 106 public Month getMonth() { 107 return month; 108 } 109 public void setMonth(Month month) { 110 this.month = month; 111 } 112 public Year getYear() { 113 return year; 114 } 115 public void setYear(Year year) { 116 this.year = year; 117 } 118 public String showDate(){//输出形式 119 String str=year.getValue()+"-"+month.getValue()+"-"+day.getValue(); 120 return str; 121 } 122 public void setDayMin() { 123 day.setValue(1); 124 } 125 public void setDayMax() { 126 day.setValue(mon_maxnum[month.getValue()-1]); 127 } 128 public boolean checkInputValidity(){//检查输入日期是否正确 129 boolean result=false; 130 if(month.validate()&&year.validate()) 131 result=true; 132 return result; 133 } 134 public boolean compareDates(DateUtil date){//比较两日期大小 135 boolean result=false; 136 if(this.getYear().getValue()>date.getYear().getValue()) 137 result=true; 138 else if(this.getYear().getValue()==date.getYear().getValue()&&this.getMonth().getValue()>date.getMonth().getValue()) 139 result=true; 140 else if(this.getYear().getValue()==date.getYear().getValue()&&this.getMonth().getValue()==date.getMonth().getValue()&&this.getDay().getValue()>date.getDay().getValue()) 141 result=true; 142 return result; 143 } 144 public boolean equalTwoDates(DateUtil date){//检查两日期是否相等 145 boolean result=true; 146 if(this.getYear().getValue()!=date.getYear().getValue()) 147 result=false; 148 else if(this.getMonth().getValue()!=date.getMonth().getValue()) 149 result=false; 150 else if(this.getDay().getValue()!=date.getDay().getValue()) 151 result=false; 152 return result; 153 } 154 public DateUtil getNextNDays(int n){//求下N天 155 while(n>365){//大于一年时 156 if(this.getMonth().getValue()<=2){//判断该年是否为闰年 157 if(this.getYear().isLeapYear()){ 158 n=n-366; 159 this.getYear().yearIncrement(); 160 } 161 else{ 162 n=n-365; 163 this.getYear().yearIncrement(); 164 } 165 } 166 else if(this.getMonth().getValue()>2){ 167 this.getYear().yearIncrement();//判断下一年是否为闰年 168 if(this.getYear().isLeapYear()){ 169 n=n-366; 170 } 171 else{ 172 n=n-365; 173 } 174 } 175 } 176 for(int i=0;i<n;i++){//小于一年时 177 this.getDay().dayIncrement(); 178 if(this.getYear().isLeapYear()){//判断该年是否为闰年 179 this.mon_maxnum[1]=29; 180 } 181 else 182 this.mon_maxnum[1]=28; 183 if(this.getDay().getValue()>this.mon_maxnum[this.getMonth().getValue()-1]){ 184 this.getMonth().monthIncrement();//月份进位 185 this.setDayMin(); 186 if(this.getMonth().getValue()>12){ 187 this.getYear().yearIncrement();//年份进位 188 this.getMonth().reseMin(); 189 } 190 } 191 } 192 return this; 193 } 194 195 public DateUtil getPreviousNDays(int n){//求前N天 196 while(n>365){//大于一年时 197 if(this.getMonth().getValue()>2){ 198 if(this.getYear().isLeapYear()){//判断该年是否为闰年 199 this.getYear().yearReduction(); 200 n=n-366; 201 } 202 else{ 203 this.getYear().yearReduction(); 204 n=n-365; 205 } 206 } 207 else if(this.getMonth().getValue()<=2){ 208 this.getYear().yearReduction();//判断前一年年是否为闰年 209 if(this.getYear().isLeapYear()){ 210 n=n-366; 211 } 212 else{ 213 n=n-365; 214 } 215 } 216 } 217 for(int i=0;i<n;i++){//小于一年时 218 this.getDay().dayReduction(); 219 if(this.getDay().getValue()<=0){//判断该年是否为闰年 220 if(this.getYear().isLeapYear()){ 221 this.mon_maxnum[1]=29; 222 } 223 else 224 this.mon_maxnum[1]=28; 225 this.getMonth().monthReduction();; 226 if(this.getMonth().getValue()<=0){//往后退一年 227 this.getYear().yearReduction(); 228 this.getMonth().reseMax(); 229 } 230 this.setDayMax(); 231 } 232 } 233 return this; 234 } 235 public int getDaysofDates(DateUtil date){//求两日期之间的天数 236 int gap=0; 237 if(this.compareDates(date)){//第一个日期大于第二个,求的方法与求前n天大致一样 238 while(this.getYear().getValue()-date.getYear().getValue()>=2){ 239 if(this.getMonth().getValue()>2){ 240 if(this.getYear().isLeapYear()){ 241 gap+=366; 242 } 243 else 244 gap+=365; 245 this.getYear().yearReduction(); 246 } 247 if(this.getMonth().getValue()<=2){ 248 this.getYear().yearReduction(); 249 if(this.getYear().isLeapYear()){ 250 gap+=366; 251 } 252 else 253 gap+=365; 254 } 255 } 256 while(true){ 257 if(this.equalTwoDates(date)){ 258 break; 259 } 260 gap++; 261 this.getDay().dayReduction(); 262 if(this.getDay().getValue()<=0){ 263 this.getMonth().monthReduction(); 264 if(this.getMonth().getValue()<=0){ 265 this.getYear().yearReduction(); 266 this.getMonth().reseMax(); 267 } 268 if(this.getYear().isLeapYear()){ 269 this.mon_maxnum[1]=29; 270 } 271 else 272 this.mon_maxnum[1]=28; 273 this.setDayMax(); 274 } 275 } 276 } 277 else{//第一个日期小于第二个,求的方法与求后n天大致一样 278 while(date.getYear().getValue()-this.getYear().getValue()>=2){ 279 if(this.getMonth().getValue()>2){ 280 this.getYear().yearIncrement(); 281 if(this.getYear().isLeapYear()){ 282 gap+=366; 283 } 284 else 285 gap+=365; 286 } 287 if(this.getMonth().getValue()<=2){ 288 if(this.getYear().isLeapYear()){ 289 gap+=366; 290 } 291 else 292 gap+=365; 293 this.getYear().yearIncrement(); 294 } 295 296 } 297 while(true){ 298 if(this.equalTwoDates(date)){ 299 break; 300 } 301 gap++; 302 this.getDay().dayIncrement(); 303 if(this.getYear().isLeapYear()){ 304 this.mon_maxnum[1]=29; 305 } 306 else 307 this.mon_maxnum[1]=28; 308 if(this.getDay().getValue()>this.mon_maxnum[this.getMonth().getValue()-1]){ 309 this.getMonth().monthIncrement(); 310 this.setDayMin(); 311 if(this.getMonth().getValue()>12){ 312 this.getYear().yearIncrement(); 313 this.getMonth().reseMin(); 314 } 315 316 } 317 } 318 } 319 return gap; 320 } 321 } 322 323 class Year { 324 private int value;//年份 325 326 327 public Year() {//无参构造 328 329 } 330 public Year(int value) {//有参构造 331 this.value=value; 332 } 333 public int getValue() {//value的get 334 return value; 335 } 336 337 public void setValue(int value) {//value的set 338 this.value = value; 339 } 340 public boolean isLeapYear(){//判断是否为闰年 341 boolean result=false; 342 if((value%4==0&&value%100!=0)||value%400==0) 343 result=true; 344 return result; 345 } 346 public boolean validate() {//判断输入数据是否合法 347 boolean result=false; 348 if(value<=2020&&value>=1820) { 349 result=true; 350 } 351 return result; 352 } 353 public void yearIncrement() {//年份加一 354 this.value=this.value+1; 355 } 356 public void yearReduction() {//年份减一 357 this.value=this.value-1; 358 } 359 } 360 361 class Month { 362 private int value;//月份 363 364 public Month() { //无参构造 365 366 } 367 public Month(int Value) {//有参构造 368 this.value=Value; 369 } 370 public int getValue() {//value的get 371 return value; 372 } 373 public void setValue(int value) {//value的set 374 this.value = value; 375 } 376 public void reseMin() {//月份设置最小值 377 this.value=1; 378 } 379 public void reseMax() {//月份设计最大值 380 this.value=12; 381 } 382 public boolean validate() {//判断输入数据是否合法 383 boolean result=false; 384 if(this.value>=1&&this.value<=12) { 385 result=true; 386 } 387 return result; 388 } 389 public void monthIncrement() {//月份加一 390 this.value=this.value+1; 391 } 392 public void monthReduction() {//月份减一 393 this.value=this.value-1; 394 } 395 396 } 397 398 class Day { 399 private int value;//天数 400 401 public Day() {//无参构造 402 403 } 404 public Day(int Value) {//有参构造 405 this.value=Value; 406 407 } 408 public int getValue() {//value的get 409 return value; 410 } 411 412 public void setValue(int value) {//value的set 413 this.value = value; 414 } 415 public void dayIncrement() {//天数加一 416 this.value=this.value+1; 417 } 418 public void dayReduction() {//天数减一 419 this.value=this.value-1; 420 } 421 422 }View Code
题集六7-1菜单计价程序-4
这个菜单要比之前的那个难很多,尤其是其中的输入异常判断,输入异常的判断有很多,要输出很多异常报错,既要考虑异常输出的先后顺序,还要考虑因为某个异常会忽略其他异常的输出。同时还要考虑在桌号相同的时候,看时间是否在同一时间段,来判断是不是同一记录,再进行计算价格。在数据处理上,新增了特色菜这个菜系,也就代表着之前的所有菜价加在一起再算折扣的后的总价方法要改,改成同类型的菜价格相加再去乘以折扣。同时,这个题目的输入数据判断可以用正则表达式进行初步判断,在进行接下来的操作。在这次的7-4中,新加了很多功能,我就将原先Table类中的一些功能拿了出来,我觉得Table类的功能太多,新增了Date类和Restaurant类,用于实现一些功能,减少Table类的职责,这是我所写的代码设计类图,不知道为什么我的powerdesigner逆生成类图不会有依赖关系。
三,踩坑心得
1.不管是在做什么题目时,先把题目要求看清楚,再去做,因为这个原因,导致我题集六的题目没做好,题目没有看明白,我一开始题集四7-1的代点菜设计是对的,但是我自己在做7-4是没有仔细看题,以为输出每一桌的总价钱是直接跟在每一桌的点菜记录后面,导致改掉了原来题集四7-1的输出设计,最后这个题目只做出来一点异常处理,直到题目时间截止后,我才发现我看错题目了。
2.注意所用的类的方法放回的数据类型,以及是否会返回负数,如:long weeks = date1.until(date2, ChronoUnit.WEEKS);这里weeks是可以为负数的,以及要用long类型的数据接收。
3.在做题集五7-5时要写一个方法判断输入日期数据是否合法没有写好,没有判断输入的月份是否大于12或小于1,因为判断日期输入是否正确是要用每月最大天数数组的,导致数组越界异常,这里判断异常时应该先判断年份是否异常,再判断月份是否异常,最后判断日期是否正常。
4.写菜单计价程序时,因为用到了对象数组,有时只给了对象数组一部分元素申请空间,但是在查找元素的时候,还是用简单的for循环去写,但这样那些未申请空间的数组成员都为空,就会出现对象为空的异常报错空,当然这也与我不会用Arraylist数组有关,ArrayList数组的大小不固定,可随时扩充,再配合for-each循环去做增删查改的操作,这样就不会有这种情况了。
四,总结
1.学习收获:
这三次习题集让我更熟练的运用ArrayList数组的方法,例如数组元素的添加,删除,排序。Java正则表达式的简单运用例如:matcher.find(),matchers(),只需要写出正确的匹配格式,利用Java正则表达式能够很快的匹配到符合的数据。题集四中的7-7让我了解了Java中一些好用的工具,学会了这些类的简单运用,如String类中split()等方法、Integer类中parseInt()等方法的用法,LocalDate类中of()、isAfter()、isBefore()、until()等方法,ChronoUnit类中DAYS、WEEKS、MONTHS的用法。还有就是两次菜单计价程序的失败让我知道编程时不能分心,我编程时老喜欢写一会看一会手机,题目一长点就看不下去,注意力完全不集中,写的时候有没有静下心来看题目,导致效率十分低下。
2.改进以及教训
学过的东西要灵活运用,不要一直用一些以前的东西,比如在这次的题集六7-1中,很多输入数据的格式判断是否正确都可以用正则表达式去做,但是我没有想到,只有当题目要求时,我才会想到用这些高效准确的方法,不然的话,我就只会用一些老套而且很杂乱的方法去做。而且这次pta有很多异常处理之前老师讲了异常处理的方法,但是我还是不会用,只能用一些最基础的方法去判断,以及ArrayList数组的使用,for-each循环的使用,这些都学过的东西但就是想不到,以后学过的东西要经常用才能熟练。
标签:总结,int,题集,PTA,getValue,getDay,value,public,getMonth From: https://www.cnblogs.com/BR-boru/p/17363554.html