快递管理系统——IO版
学习了 IO 以后,在上一个集合的基础 上进行迭代,将快递信息使用 IO 流的方式永久性保存到磁盘。将快递数据存储到文件中。文件存储快递信息后,可以
在每次启动应用 时读取文件中的内容,从而实现程序数据的一直存在。通过简单的思考与分析,以下是我的代码与思路。
1. 视图层(存在一些方法未使用到,可以优化)
package com.java.express;
import com.java.bean.Express;
import java.util.Random;
import java.util.Scanner;
public class Views {
private Random random = new Random();
private Scanner input = new Scanner(System.in);
public void welcome(){
System.out.println("==========欢迎使用XXX快递管理系统==========");
}
public void bye(){
System.out.println("欢迎下次使用");
}
/**
* 选择身份的菜单
*/
public int menu(){
System.out.println("请根据提示进行操作。");
System.out.println("请选择身份:");
System.out.println("1.快递员");
System.out.println("2.普通用户");
System.out.println("0.退出");
String text = input.nextLine();
int num = -1;
try {//捕获异常
//将用户输入的数据转换为整型数据
num = Integer.parseInt(text);
}catch(NumberFormatException n){
}
if(num<0 || num>2){
System.out.println("输入的数据有误,请重新输入。");
return menu();
}
return num;
}
/**
快递员菜单
*/
public int Postman(){
System.out.println("请根据提示进行操作。");
System.out.println("1.快递录入");
System.out.println("2.修改快递");
System.out.println("3.删除快递");
System.out.println("4.查看所有快递");
System.out.println("0.返回上级目录");
String text = input.nextLine();
int num = -1;
try {//捕获异常
//将用户输入的数据转换为整型数据
num = Integer.parseInt(text);
}catch(NumberFormatException n){
}
if(num<0 || num>4){
System.out.println("输入的数据有误,请重新输入。");
return Postman();
}
return num;
}
/**
快递录入方法,包含了快递单号和快递公司的快递对象
*/
public Express Insert(){
Express e = new Express();
System.out.println("请根据提示进行操作。");
System.out.println("请输入快递单号:");
String number = input.nextLine();
System.out.println("请输入快递公司:");
String company = input.nextLine();
e.setNumber(number);
e.setCompany(company);
return e;
}
/**
* 提示并接收用户输入快递单号,通过这个过程来进行下一步的对比操作
* */
public String findByNumber(){
System.out.println("请根据提示输入快递信息");
System.out.println("请输入你要操作的快递单号:");
String number = input.nextLine();
return number;
}
/**
* 显示快递信息的方法
* */
public void printExpress(String number,String company,String code,String x,String y){
System.out.println("快递信息如下:");
System.out.println("您的快递在第【"+x+"】行第【"+y+"】列。");
System.out.println("快递单号为:" + number + " 快递公司为:" + company + " 快递取件码为:" + code);
}
/**
* 更新快递信息的方法
*/
public Express Update(){
System.out.println("已查询到您即将要操作的快递");
Express e = new Express();
System.out.println("请输入新的快递单号:");
String number = input.nextLine();
System.out.println("请输入新的快递公司:");
String company = input.nextLine();
e.setCompany(company);
e.setNumber(number);
return e;
}
/**
* 询问是否确认删除
* */
public int delete(){
System.out.println("是否确认删除?");
System.out.println("1.确认删除");
System.out.println("2.取消删除");
String text = input.nextLine();
int num = -1;
try {//捕获异常
//将用户输入的数据转换为整型数据
num = Integer.parseInt(text);
}catch(NumberFormatException n){
}
if(num<1 || num>2){
System.out.println("输入的数据有误,请重新输入。");
return delete();
}
return num;
}
/**
用户菜单
*/
public int User(){
System.out.println("请输入取件码:");
String code = input.nextLine();
int num = -1;
try {/*
捕获异常
将用户输入的数据转换为整型数据
*/
num = Integer.parseInt(code);
}catch(NumberFormatException n){
}
if(num<100000 || num>999999){
System.out.println("输入的数据有误,请重新输入。");
return User();
}
return num;
}
/**
* 快件已存在时提示用户
* */
public void expressExist(){
System.out.println("快递已存在,请勿重复存储");
}
/**
* 快递柜已满时提示用户
* */
public void Full(){
System.out.println("快递柜已满,不可继续存入");
}
/**
* 快件不存在时提示用户
* */
public void expressNull(){
System.out.println("您查找的快递不存在,请检查输入");
}
/**
* 提示用户取件码
* */
public void printCode(Express e){
System.out.println("存储成功,快件的取件码为:"+e.getCode());
}
public void success(){
System.out.println("操作成功");
}
}
2. 数据层(DAO)
package com.java.dao;
import com.java.bean.Express;
import com.java.express.Views;
import java.io.*;
import java.util.Properties;
import java.util.Random;
public class ExpressDao {
private Random random = new Random();
private static Views views = new Views();
private int size = 1; //现有快递数
/**
* 录入快递的数据操作方法
* */
public Express add(Express e) throws IOException {
FileReader fr = new FileReader("express.properties");
Properties p = new Properties();
Views views = new Views();
p.load(fr);
if (findByNumber(e.getNumber())){
views.expressExist();
} else if (size == 100){
views.Full();
}else{
if (p.get("Size") != null) {
size = (Integer.parseInt((String) p.get("Size"))) + 1; //快递数++
}
p.putIfAbsent("Size", "0");
FileWriter fw = new FileWriter("express.properties");
String x = String.valueOf(random.nextInt(10));
String y = String.valueOf(random.nextInt(10));
String z = String.valueOf(size);
p.put("Number"+size,e.getNumber());
p.put("Company"+size,e.getCompany());
String code = String.valueOf(randomCode());
p.put("Code"+size,code);
p.put("Local-x"+size,x);
p.put("Local-y"+size,y);
p.put("Size",z);
p.store(fw,"New Data");
fw.close();
fr.close();
e.setCode(Integer.parseInt(code));
e.setX(x);
e.setY(y);
return e;
}
fr.close();
return null;
}
/**
* 随机生成取件码的方法
* */
public int randomCode() throws IOException {
while (true){
int code = random.nextInt(900000)+100000;
if (findByCode(code) == false) {
return code;
}
}
}
/**
* 删除快递的数据操作方法
* */
public void delete(String number) throws IOException {
FileReader fr = new FileReader("express.properties");
Properties p = new Properties();
p.load(fr);
if (!Empty()) {
if ( p.get("Size") != null) {
for (int i = 0;i <= Integer.parseInt((String)p.get("Size"));i++){
if (p.get("Number" + i) != null) {
if ((p.get("Number" + i).equals(number))) {
String size = String.valueOf(Integer.parseInt((String) p.get("Size")) - 1);
p.remove("Number" + i);
p.remove("Company" + i);
p.remove("Code" + i);
p.remove("Local-x" + i);
p.remove("Local-y" + i);
p.remove("Size" + i);
p.put("Size", size);
FileWriter fw = new FileWriter("express.properties");
p.store(fw, "Data");
fw.close();
fr.close();
break;
}
}
}
}
}
fr.close();
}
/**
* 在用户取完快递后删除快递信息
* */
public void deleteAfterPick(int code) throws IOException {
FileReader fr = new FileReader("express.properties");
Properties p = new Properties();
p.load(fr);
if (!Empty()) {
if ( p.get("Size") != null) {
for (int i = 0;i <= Integer.parseInt((String)p.get("Size"));i++){
if (p.get("Code"+i)!=null) {
if (p.get("Code" + i).equals(String.valueOf(code))) {
String size = String.valueOf(Integer.parseInt((String) p.get("Size")) - 1);
views.printExpress((String) p.get("Number" + i), (String) p.get("Company" + i), (String) p.get("Code" + i), (String) p.get("Local-x" + i), (String) p.get("Local-y" + i));
p.remove("Number" + i);
p.remove("Company" + i);
p.remove("Code" + i);
p.remove("Local-x" + i);
p.remove("Local-y" + i);
p.remove("Size" + i);
p.put("Size",size);
FileWriter fw = new FileWriter("express.properties");
p.store(fw, "Data");
fw.close();
fr.close();
break;
}
}
}
}
}
fr.close();
}
/**
* 更新数据
* */
public void update(Express e1,Express e2) throws IOException {
FileReader fr = new FileReader("express.properties");
Properties p = new Properties();
p.load(fr);
for (int i = 0;i <= Integer.parseInt((String)p.get("Size"));i++){
if (p.get("Number"+i) != null) {
if (p.get("Number" + i).equals(e1.getNumber())) {
FileWriter fw = new FileWriter("express.properties");
p.put("Number"+i,e2.getNumber());
p.put("Company" + i, e2.getCompany());
String code = String.valueOf(randomCode());
p.put("Code" + i, code);
String x = String.valueOf(random.nextInt(10));
String y = String.valueOf(random.nextInt(10));
p.put("Local-x" + i, x);
p.put("Local-y" + i, y);
p.store(fw, "Data");
fw.close();
fr.close();
break;
}
}
}
fr.close();
}
/**
* 在快递员更新前后快递信息后打印显示
* */
public Express updatePrint(String number) throws IOException {
FileReader fr = new FileReader("express.properties");
Properties p = new Properties();
Express e = new Express();
p.load(fr);
for (int i = 0;i <= Integer.parseInt((String)p.get("Size"));i++){
if (p.get("Number"+i) != null) {
if (p.get("Number" + i).equals(number)) {
String num = String.valueOf(p.get("Number" + i));
String com = String.valueOf(p.get("Company" + i));
String code = String.valueOf(p.get("Code" + i));
String local1 = String.valueOf(p.get("Local-x" + i));
String local2 = String.valueOf(p.get("Local-y" + i));
e.setNumber(num);
e.setCompany(com);
e.setCode(Integer.parseInt(code));
e.setX(local1);
e.setY(local2);
System.out.println("快递公司:" + p.get("Company" + i) + ", 快递单号:" + p.get("Number" + i) + ", 取件码:" + p.get("Code" + i));
return e;
}
}
}
fr.close();
return null;
}
/**
* 通过快递单号查找快递的方法
* */
public Boolean findByNumber(String number) throws IOException {
FileReader fr = new FileReader("express.properties");
Properties p = new Properties();
p.load(fr);
if (!Empty()) {
if ( p.get("Size") != null) {
for (int i = 0; i <= Integer.parseInt((String) p.get("Size")); i++) { //遍历输出
if (p.get("Number"+i) != null) {
if (p.get("Number" + i).equals(number)) { //单号重复
return true;
}
}
}
}
}
fr.close();
return false;
}
/**
* 通过快递取件码查找快递的方法
* */
public Boolean findByCode(int code) throws IOException {
FileReader fr = new FileReader("express.properties");
Properties p = new Properties();
p.load(fr);
if (!Empty()) {
if ( p.get("Size") != null) {
for (int i = 0; i <= Integer.parseInt((String) p.get("Size")); i++) { //遍历输出
if (p.get("Code"+i) != null) {
if (p.get("Code" + i).equals(String.valueOf(code))) { //单号重复
return true;
}
}
}
}
}
fr.close();
return false;
}
/**
* 查找并打印所有快递的方法
* */
public void findPrintAll() throws IOException {
FileReader fr = new FileReader("express.properties");
Properties p = new Properties();
p.load(fr);
if (!Empty()) { //判断是否为空
for (int i = 0; i <= Integer.parseInt((String) p.get("Size")); i++) { //遍历输出
System.out.println("第" + (p.get("Local-x" + i)) + "排, 第" + (p.get("Local-y" + i)) + "列快递,");
System.out.println("快递信息如下");
System.out.println("快递公司:" + p.get("Company" + i) + ", 快递单号:" + p.get("Number" + i) + ", 取件码:" + p.get("Code" + i));
}
} else {
System.out.println("无快递");
}
fr.close();
}
public boolean Empty() throws IOException { //判断是否为空
FileReader r = new FileReader("express.properties");
Properties p = new Properties();
p.load(r);
if (p.get("Size") != null) { //文件为空
if (Integer.parseInt((String) p.get("Size")) == 0) { //快递数为0
return true;
}
return false;
}
return true;
}
}
3. 快递类(包含基础的属性和方法)
package com.java.bean;
import java.util.Objects;
/*
快递类
*/
public class Express {
private String number; //单号
private String company; //公司
private int code; //取件码
private String x;
private String y;
public String getX() {
return x;
}
public void setX(String x) {
this.x = x;
}
public String getY() {
return y;
}
public void setY(String y) {
this.y = y;
}
/*
* 全参构造方法
* */
public Express(String number, String company, int code) {
this.number = number;
this.company = company;
this.code = code;
}
/*
* 无参构造方法
* */
public Express() {
}
@Override
public String toString() {
return "express{" +
"number='" + number + '\'' +
", company='" + company + '\'' +
", code=" + code +
'}';
}
/*
* 只比较取件码是否相同
* */
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Express express = (Express) o;
return Objects.equals(number, express.number);
}
@Override
public int hashCode() {
return 0;
}
public String getNumber() {
return number;
}
public void setNumber(String number) {
this.number = number;
}
public String getCompany() {
return company;
}
public void setCompany(String company) {
this.company = company;
}
public int getCode() {
return code;
}
public void setCode(int code) {
this.code = code;
}
}
4. 主程序(main)
package com.java.main;
import com.java.bean.Express;
import com.java.dao.ExpressDao;
import com.java.express.Views;
import java.io.File;
import java.io.IOException;
public class Main {
/**
* 初始化视图对象和数据对象
*/
private static Views v = new Views();
private static ExpressDao dao = new ExpressDao();
public static void main(String[] args) throws IOException {
File files = new File("express.properties");
files.createNewFile();
//欢迎
v.welcome();
m:while (true) {
int menu = v.menu();
switch (menu) {
case 0:
break m;
case 1: //主菜单的三种情况
cClient();
break;
case 2:
uClient();
break;
}
}
v.bye();
}
/**
* 用户菜单
* */
private static void uClient() throws IOException {
int code = v.User();
if (dao.findByCode(code)){
dao.deleteAfterPick(code);
v.success();
}else{
v.expressNull();
}
}
/**
* 快递员菜单
* */
private static void cClient() throws IOException {
while (true) {
int menu = v.Postman();
switch (menu) {
case 0:
return;
case 1: {
//1.视图层提示用户输入,将诶受用户输入的数据
Express e = v.Insert();
//2.查询快递是否已被存储
//3.数据层对数据进行存储
if (dao.findByNumber(e.getNumber())){
//快递已存在
v.expressExist();
}else{
//未存储过
Express e1 = dao.add(e);
v.printCode(e1);
v.printExpress(e1.getNumber(),e1.getCompany(), String.valueOf(e1.getCode()),e1.getX(),e1.getY());
}
}
break;
case 2:{//快递修改
//1.接收快递信息
String number = v.findByNumber();
//2.查找快递单号
if (dao.findByNumber(number)){//能查找到该快递
Express e1 = dao.updatePrint(number);
Express e2 = v.Update();
dao.update(e1,e2);
v.success();
dao.updatePrint(e2.getNumber());
}else{
v.expressNull();
}
}
break;
case 3:{//删除快递
//1.接收用户输入
String number = v.findByNumber();
//2.查询快递
if (dao.findByNumber(number)){
int type = v.delete();
if (type == 1){
dao.delete(number);
v.success();
}
}else {
v.expressNull();
}
}
break;
case 4:{//打印所有快递信息
dao.findPrintAll();
}
break;
}
}
}
}
以上是本次系统的全部代码,保存起来方便以后查阅和改善。
我的存储方式还是有很大的缺陷,序列化和反序列化更为稳妥。