java入门第二季 答答租车系统

目标

java编写一个控制台版的“答答租车系统”

功能

  • 展示所有可租车辆
  • 选择车型、租车量
  • 展示租车清单,包含:总金额、总载货量及其车型、总载人量及其车型

三大分析

数据模型分析

业务模型分析

显示和流程分析

代码如下

闲话少说,下面放出代码。

首先定义了基础的Car类:

  1. //文件名:Car.java
  2. package com.liuyanzhao;
  3. //新建Car类
  4. public abstract class Car {
  5.     private String type;
  6.     private int price;
  7.     public String getType() {
  8.         return type;
  9.     }
  10.     public void setType(String type) {
  11.         this.type = type;
  12.     }
  13.     public int getPrice() {
  14.         return price;
  15.     }
  16.     public void setPrice(int price) {
  17.         this.price = price;
  18.     }
  19.     @Override
  20.     public String toString() {
  21.         return type + "\t" + price;
  22.     }
  23. }
 

随后定义两个接口,分别对应载客与载货。

这两个接口其实不是必须,在这里是为了规定载客与载货车辆必须要有getter与setter方法。
  1. //文件名:IPassenger
  2. package com.liuyanzhao;
  3. //新建接口IPassenger,保证可载客车辆一定有如下方法
  4. public interface IPassenger {
  5.     public int getPassCapacity();
  6.     public void setPassCapacity(int passCapacity);
  7. }
 
  1. //文件名:ICargo.java
  2. package com.liuyanzhao;
  3. //新建接口ICargo,保证可载货车辆一定有如下方法
  4. public interface ICargo {
  5.     public int getCargoCapacity();
  6.     public void setCargoCapacity(int cargoCapacity);
  7. }

随后,定义了三个Car的子类:

  1. //文件名:CarBus.java
  2. package com.liuyanzhao;
  3. //新建CarBus类,作为客车,仅能载客
  4. public class CarBus extends Car implements IPassenger {
  5.     private int passCapacity;
  6.     public CarBus(String type, int price, int passCapacity) {
  7.         this.setType(type);
  8.         this.setPrice(price);
  9.         this.setPassCapacity(passCapacity);
  10.     }
  11.     public int getPassCapacity() {
  12.         return passCapacity;
  13.     }
  14.     public void setPassCapacity(int passCapacity) {
  15.         this.passCapacity = passCapacity;
  16.     }
  17.     @Override
  18.     public String toString() {
  19.         return super.toString() + "\t" + passCapacity + "\t---";
  20.     }
  21. }
 
  1. //文件名:CarTruck.java
  2. package com.liuyanzhao;
  3. //新建CarTruck类,作为货车,只能载货
  4. public class CarTruck extends Car implements ICargo {
  5.     private int cargoCapacity;
  6.     public CarTruck(String type, int price, int cargoCapacity) {
  7.         this.setType(type);
  8.         this.setPrice(price);
  9.         this.setCargoCapacity(cargoCapacity);
  10.     }
  11.     public int getCargoCapacity() {
  12.         return cargoCapacity;
  13.     }
  14.     public void setCargoCapacity(int cargoCapacity) {
  15.         this.cargoCapacity = cargoCapacity;
  16.     }
  17.     @Override
  18.     public String toString() {
  19.         return super.toString() + "\t---\t" + cargoCapacity;
  20.     }
  21. }
 
  1. //文件名:CarPickup.java
  2. package com.liuyanzhao;
  3. //新建CarPickup类,作为皮卡,既能载客,也能载货
  4. public class CarPickup extends Car implements IPassenger, ICargo {
  5.     private int passCapacity;
  6.     private int cargoCapacity;
  7.     public CarPickup(String type, int price, int passCapacity, int cargoCapacity) {
  8.         this.setType(type);
  9.         this.setPrice(price);
  10.         this.setPassCapacity(passCapacity);
  11.         this.setCargoCapacity(cargoCapacity);
  12.     }
  13.     public int getPassCapacity() {
  14.         return passCapacity;
  15.     }
  16.     public void setPassCapacity(int passCapacity) {
  17.         this.passCapacity = passCapacity;
  18.     }
  19.     public int getCargoCapacity() {
  20.         return cargoCapacity;
  21.     }
  22.     public void setCargoCapacity(int cargoCapacity) {
  23.         this.cargoCapacity = cargoCapacity;
  24.     }
  25.     @Override
  26.     public String toString() {
  27.         return super.toString() + "\t" + passCapacity + "\t" + cargoCapacity;
  28.     }
  29. }
 

主程序:

  1. //文件名:Initial.java
  2. package com.liuyanzhao;
  3. /* 答答租车系统稳定版 v1.0 by Bambrow
  4.  * 该系统读取用户输入的一切内容,并给出相应提示,确保用户输入的内容准确。
  5.  * 对用户输入字符串或其他数据类型的情况,有相应的报错及提示重新输入的功能。
  6.  * 可让用户选择一次性租用多种车辆,并对每一车辆设置单独的租车数目与租车天数。
  7.  * 可修改代码的initCarList方法,任意添加新车辆,无需修改其他任何代码。
  8.  * 作者会继续进行维护和改进,可能以后会增加管理员系统。
  9.  * 可任意参考,转载请注明作者或保留该注释。
  10.  */
  11. // 导入包
  12. import java.util.ArrayList;
  13. import java.util.List;
  14. import java.util.Scanner;
  15. import java.util.stream.IntStream;
  16. public class Initial {
  17.     public static void main(String[] args) {
  18.         System.out.println("欢迎来到答答租车系统!");
  19.         List carList = initCarList(); // 为了保证随时添加与删除项目,使用List功能
  20.         for (;;) { // 设置无条件循环
  21.             System.out.println("若您是租车客户,请输入1;" + "退出请输入0。");
  22.             int choice;
  23.             try {
  24.                 choice = Integer.parseInt(getInput());
  25.             } catch (Exception e) {
  26.                 System.out.println("指令有误!请输入正确的指令。");
  27.                 continue;
  28.             } // 确保输入的为数字,而不是别的字符
  29.             if (choice == 0)
  30.                 break// 若输入0,结束循环
  31.             else if (choice == 1) {
  32.                 rentCars(carList); // 若输入1,开始租车
  33.                 System.out.println();
  34.             } else {
  35.                 System.out.println("指令有误!请输入正确的指令。");
  36.                 continue;
  37.             } // 若输入其他数字,重新开始循环
  38.         }
  39.         System.out.println("感谢您使用答答租车系统!");
  40.     }
  41.     // 生成初始化的可租车列表
  42.     private static List initCarList() {
  43.         List<Car> carList = new ArrayList<Car>(); // 初始化List,确保每一项都是Car类
  44.         carList.add(new CarBus("小型客车"5006));
  45.         carList.add(new CarBus("大型客车"100015));
  46.         carList.add(new CarTruck("小型货车"4002));
  47.         carList.add(new CarTruck("大型货车"80010));
  48.         carList.add(new CarPickup("小型皮卡"50021));
  49.         carList.add(new CarPickup("大型皮卡"90042));
  50.         return carList; // 添加完每一辆车后返回List
  51.     } // 可以随时使用carList.add添加新车辆,而无需修改其他任何代码
  52.     // 输出租车列表,用到了每一类中重写的toString方法
  53.     private static void printCarList(List carList) {
  54.         System.out.println("以下是可用车型:");
  55.         System.out.println("序号\t车型\t租金\t载客量\t载货量");
  56.         for (int i = 0; i < carList.size(); i++) {
  57.             System.out.println((i + 1) + "\t" + (carList.get(i)).toString());
  58.         }
  59.     }
  60.     // 客户选车功能,该功能无需用户提前输入租车的类型数目,因此全部使用无需预先确定长度的List功能
  61.     private static List selectCars(List carList) {
  62.         List<Integer> rentArray = new ArrayList<Integer>(); // 储存客户选过的序号
  63.         List<Car> selectCars = new ArrayList<Car>(); // 储存用户选过的车
  64.         System.out.println("请输入租车序号,以回车分隔。输入0结束输入:");
  65.         for (;;) {
  66.             System.out.println("请输入车辆序号(1-" + carList.size() + "):");
  67.             boolean repeated = false;
  68.             int carNum;
  69.             try {
  70.                 carNum = Integer.parseInt(getInput());
  71.             } catch (Exception e) {
  72.                 System.out.println("输入不正确!请输入正确的序号。");
  73.                 continue;
  74.             } // 确保输入的为数字,而不是其他字符
  75.             if (carNum == 0)
  76.                 break// 输入0,退出循环
  77.             else if (carNum > 0 && carNum <= carList.size()) { // 确保输入的数字在范围内
  78.                 for (int i = 0; i < rentArray.size(); i++) {
  79.                     if (carNum == rentArray.get(i)) {
  80.                         System.out.println("您已输入过该车型!请重新输入序号。");
  81.                         repeated = true;
  82.                         break// 若输入的序号已经选择过,则输出选择重复信息并重新选择
  83.                     }
  84.                 }
  85.                 if (!repeated) {
  86.                     rentArray.add(carNum);
  87.                     selectCars.add((Car) carList.get(carNum - 1));
  88.                 } // 若输入的序号不重复,则加入选择的车辆列表
  89.             } else {
  90.                 System.out.println("输入不正确!请输入正确的序号。");
  91.                 continue;
  92.             } // 确保输入的数字在范围内
  93.         }
  94.         return selectCars; // 返回选好的车辆List
  95.     }
  96.     // 读取租车数目功能
  97.     private static int rentCount() {
  98.         for (;;) {
  99.             System.out.println("请输入租车数(1-50):");
  100.             int rentCount;
  101.             try {
  102.                 rentCount = Integer.parseInt(getInput());
  103.             } catch (Exception e) {
  104.                 System.out.println("输入不正确!请输入正确的租车数。");
  105.                 continue;
  106.             } // 确保输入的为数字,而不是其他字符
  107.             if (rentCount >= 1 && rentCount <= 50)
  108.                 return rentCount; // 输入正确
  109.             else
  110.                 System.out.println("输入不正确!请输入正确的租车数。"); // 输入不正确
  111.         }
  112.     }
  113.     // 对每一种选好的车辆,读取相应的租车数目
  114.     private static int[] rentNumArray(List carList) {
  115.         int[] rentNumArray = new int[carList.size()]; // 使用数组存储每一种车辆的数目
  116.         for (int i = 0; i < carList.size(); i++) {
  117.             System.out.println("请输入选定列表里,第" + (i + 1) + "辆车的租车数量:");
  118.             rentNumArray[i] = rentCount(); // 调用读取租车数目方法
  119.         }
  120.         return rentNumArray; // 返回租车数目数组
  121.     }
  122.     // 读取租车天数功能
  123.     private static int rentDays() {
  124.         for (;;) {
  125.             System.out.println("请输入租车天数(1-365):");
  126.             int rentDays;
  127.             try {
  128.                 rentDays = Integer.parseInt(getInput());
  129.             } catch (Exception e) {
  130.                 System.out.println("输入不正确!请输入正确的租车天数。");
  131.                 continue;
  132.             } // 确保输入的为数字,而不是其他字符
  133.             if (rentDays >= 1 && rentDays <= 365)
  134.                 return rentDays; // 输入正确
  135.             else
  136.                 System.out.println("输入不正确!请输入正确的租车天数。"); // 输入不正确
  137.         }
  138.     }
  139.     // 对每一种选好的车辆,读取相应的租车天数
  140.     private static int[] rentDayArray(List carList) {
  141.         int[] rentDayArray = new int[carList.size()]; // 使用数组存储每一种车辆的天数
  142.         for (int i = 0; i < carList.size(); i++) {
  143.             System.out.println("请输入选定列表里,第" + (i + 1) + "辆车的租车天数:");
  144.             rentDayArray[i] = rentDays(); // 调用读取租车天数方法
  145.         }
  146.         return rentDayArray; // 返回租车天数数组
  147.     }
  148.     // 打印订单
  149.     private static void printOrder(List carList, int[] rentNumArray, int[] rentDayArray) {
  150.         int[] rentSinglePriceTotal = new int[carList.size()];
  151.         int[] rentSinglePassTotal = new int[carList.size()];
  152.         int[] rentSingleCargoTotal = new int[carList.size()];
  153.         // 三个数组分别存储总价、总载客量与总载货量
  154.         System.out.println("以下是您的订单:");
  155.         System.out.println("序号\t车型\t租金\t载客量\t载货量" + "\t租用数量\t租用天数\t消费数额");
  156.         for (int i = 0; i < carList.size(); i++) {
  157.             rentSinglePriceTotal[i] = ((Car) carList.get(i)).getPrice() * rentNumArray[i] * rentDayArray[i]; // 计算每一种车的总价
  158.             System.out.println((i + 1) + "\t" + (carList.get(i)).toString() + "\t" + rentNumArray[i] + "\t"
  159.                     + rentDayArray[i] + "\t" + rentSinglePriceTotal[i]);
  160.             try {
  161.                 rentSinglePassTotal[i] = ((CarBus) carList.get(i)).getPassCapacity() * rentNumArray[i];
  162.             } catch (Exception eCarBus) {
  163.                 try {
  164.                     rentSinglePassTotal[i] = ((CarPickup) carList.get(i)).getPassCapacity() * rentNumArray[i];
  165.                 } catch (Exception eCarPickup) {
  166.                     rentSinglePassTotal[i] = 0;
  167.                 }
  168.             } // 双重try嵌套,如果车辆有载客功能,则存储一天的总载客量,否则存储0
  169.             try {
  170.                 rentSingleCargoTotal[i] = ((CarTruck) carList.get(i)).getCargoCapacity() * rentNumArray[i];
  171.             } catch (Exception eCarTruck) {
  172.                 try {
  173.                     rentSingleCargoTotal[i] = ((CarPickup) carList.get(i)).getCargoCapacity() * rentNumArray[i];
  174.                 } catch (Exception eCarPickup) {
  175.                     rentSingleCargoTotal[i] = 0;
  176.                 }
  177.             } // 双重try嵌套,如果车辆有载货功能,则存储一天的总载货量,否则存储0
  178.         }
  179.         int rentTotal = IntStream.of(rentSinglePriceTotal).sum();
  180.         int passCapacityTotal = IntStream.of(rentSinglePassTotal).sum();
  181.         int cargoCapacityTotal = IntStream.of(rentSingleCargoTotal).sum();
  182.         // 将三个数组的值分别相加求和
  183.         System.out.println("总载客量(人/天):" + passCapacityTotal);
  184.         System.out.println("总载货量(人/天):" + cargoCapacityTotal);
  185.         System.out.println("订单总价(元):" + rentTotal); // 所有车的订单总价
  186.     }
  187.     // 读取用户输入方法
  188.     private static String getInput() {
  189.         Scanner input = new Scanner(System.in); // 新建Scanner
  190.         try {
  191.             return input.next();
  192.         } catch (Exception e) {
  193.             return null// 确保用户输入了内容
  194.         } finally {
  195.             input.nextLine(); // 防止下次调用时出现读取错误
  196.         }
  197.     }
  198.     // 开始租车
  199.     private static void rentCars(List carList) {
  200.         printCarList(carList); // 打印现有的车辆列表
  201.         List selectCars = selectCars(carList); // 用户开始选车
  202.         System.out.println("这是您选定的租车列表:");
  203.         printCarList(selectCars); // 打印选定的车辆列表
  204.         int[] rentNumArray = rentNumArray(selectCars); // 用户对每一种车输入租车数量
  205.         int[] rentDayArray = rentDayArray(selectCars); // 用户对每一种车输入租车天数
  206.         printOrder(selectCars, rentNumArray, rentDayArray); // 打印最终订单
  207.     }
  208. }

发表评论

目前评论:4

  • avatar 菊部

    点进来看图的。。结果。,。

  • avatar 天下磨浆机

    支持支持支持

  • avatar 星空游戏

    感谢分享