Chapter09 项目 房屋出租系统(面向对象中级)

9.1 房屋出租系统-需求

9.1.1项目需求说明

  • 实现基于文本界面的《房屋出租软件》。
  • 能够实现对房屋信息的添加、修改和删除(用数组实现),并能够打印房屋明细表

9.2 房屋出租系统-界面

9.2.1项目界面 - 主菜单

9.2.2项目界面- 新增房源

9.2.3项目界面- 查找房源

9.2.4项目界面- 删除房源

9.2.5项目界面- 修改房源

9.2.6项目界面- 房屋列表

9.2.7项目界面- 退出系统

9.3 房屋出租系统-设计(!!)

  • 项目设计-程序框架图 (分层模式=>当软件比较复杂,需要模式管理)

代码实现:

主类:运行

package com.lxd.hoserent;

import com.lxd.hoserent.view.HouseView;

public class HouseRentApp {
public static void main(String[] args) {
//创建HouseView对象,并且显示主菜单,是整个程序的入口
new HouseView().mainMenu();
System.out.println("===你退出房屋出租系统=== ");
}
}

House的对象表示一个房屋需要那些信息

package com.lxd.hoserent.domain;

/*
*House的对象表示一个房屋信息
*/
public class House {
//编号 房主 电话 地址 月租 状态(未出租/已出租)
private int id;
private String name;
private String phone;
private String address;
private int rent;
private String state; //构造器和getter,setter public House(int id, String name, String phone, String address, int rent, String state) {
this.id = id;
this.name = name;
this.phone = phone;
this.address = address;
this.rent = rent;
this.state = state;
} public int getId() {
return id;
} public void setId(int id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public String getPhone() {
return phone;
} public void setPhone(String phone) {
this.phone = phone;
} public String getAddress() {
return address;
} public void setAddress(String address) {
this.address = address;
} public int getRent() {
return rent;
} public void setRent(int rent) {
this.rent = rent;
} public String getState() {
return state;
} public void setState(String state) {
this.state = state;
} //为了方便的输出对象信息,我们实现toString方法
//编号 房主 电话 地址 月租 状态(未出租/已出租)
@Override
public String toString() {
return id +
"\t\t" + name +
"\t" + phone +
"\t\t" + address +
"\t "+ rent +
"\t" + state ;
}
}

服务类:运行的程序,隐藏在后端

package com.lxd.hoserent.service;

import com.lxd.hoserent.domain.House;

/**
* HouseService.java <=> 类 【业务层】
* 定义 House[],保存 House对象
* 1.响应HouseView的调用
* 2.完成对房屋信息的各种操作(增删改查 c [creat] r [read] u[update] d[delete])
*/
public class HouseService {
private House[] houses;//保存House对象
private int houseNums = 1;//记录当前有多少个房屋信息
private int idCounter = 1;//记录当前id的个数 //构造器
public HouseService(int size) {
//new houses
houses = new House[size];// 当创建HouseService对象,指定数组大小
//为了配合测试列表信息,初始化一个house对象
houses[0] = new House(1, "jack", "112", "四川省", 2000, "未出租");
} //查找房屋
public House findById(int findId){
//遍历数组
for (int i = 0; i < houseNums; i++) {
if (findId == houses[i].getId()){
return houses[i];
} }
return null;
} //完成删除房屋信息 del方法
public boolean del(int delId) {
int index = -1;
for (int i = 0; i < houseNums; i++) {
if (delId == houses[i].getId()) {//要删除的房屋(id),是数组下标为 i 的元素
index = i;//就使用index接收i
}
}
if (index == -1) {//说明delId在数组中不存在
return false;
} for (int i = index; i < houseNums - 1; i++) {
houses[i] = houses[i + 1];
}
houses[--houseNums] = null;//把当有存在的房屋信息的最后一个,设置为null
return true;
} //add方法,添加新对象,返回boolean
public boolean add(House newHouse) {
//判断是否还可以继续添加(我们暂时不考虑数组扩容的问题)
if (houseNums == houses.length) {//不能再添加
System.out.println("添加已满");
return false;
}
//new House对象加入到,新增加了一个房屋
houses[houseNums++] = newHouse;//简写,直接后++,运行完了,再自增加一地址码
// houseNums++;
//我们程序员需要自己需要设计一个id自增长的机制,更新newHouse的id。
// idCounter++;
newHouse.setId(++idCounter);//完成加入新的房屋,id也会改变,自增加一id的数值
return true;
} //list方法,返回数组
public House[] list() {
return houses;
}
}

界面类:显示界面,并调用服务类里面的方法,并接受用户的输入

package com.lxd.hoserent.view;

import com.lxd.hoserent.domain.House;
import com.lxd.hoserent.service.HouseService;
import com.lxd.hoserent.utils.Utility; /**
* 1.显示界面
* 2.接受用户的输入
* 3.调用HouseService完成对房屋信息的各种操作
*/
public class HouseView {
private boolean loop = true;//控制显示菜单
private char key = ' ';//接受用户的选择
private HouseService houseService = new HouseService(10);//设置数组的大小为10 //根据Id修改房屋信息,updateHose(),修改房屋信息
public void update() {
System.out.println("=====================修改房屋信息=====================");
System.out.println("请选择待修改房屋编号(-1退出)");
int updateId = Utility.readInt();
if (updateId == -1) {
System.out.println("=====================你放弃了房屋修改=====================");
return;
} //根据输入的updateId,查找对象
//返回的是引用类型【即,就是数组的元素】
//因此后面对house.setXxx(),就会修改HouseService中数组的元素
House house = houseService.findById(updateId);
if (house == null) {
System.out.println("=====================修改房屋信息编号不存在=====================");
return;
} System.out.print("姓名(" + house.getName() + "):");
String name = Utility.readString(8, "");//这里如果用户直接回车表示不修改该信息,默认""
if (!"".equals(name)) {
house.setName(name);
} System.out.print("电话(" + house.getPhone() + "):");
String phone = Utility.readString(13, "");//这里如果用户直接回车表示不修改该信息,默认""
if (!"".equals(phone)) {
house.setPhone(phone);
} System.out.print("地址(" + house.getAddress() + "):");
String address = Utility.readString(18, "");//这里如果用户直接回车表示不修改该信息,默认""
if (!"".equals(address)) {
house.setAddress(address);
}
System.out.print("租金(" + house.getRent() + "):");
int rent = Utility.readInt(-1);//这里如果用户直接回车表示不修改该信息,默认""
if (rent != -1) {
house.setRent(rent);
} System.out.print("状态(" + house.getState() + "):");
String state = Utility.readString(3, "");//这里如果用户直接回车表示不修改该信息,默认""
if (!"".equals(state)) {
house.setState(state);
} System.out.println("=====================修改房屋信息成功====================="); } //根据id查找房屋信息
public void findHouse() {
System.out.println("=====================查找的信息=====================");
System.out.print("请输入你需要查找房屋的id:");
int findId = Utility.readInt();
//调用方法
House house = houseService.findById(findId);
if (house != null) {
System.out.println(house);
} else {
System.out.println("=====================查找的信息的Id不存在=====================");
} } //完成退出确认
public void exit() {
char c = Utility.readConfirmSelection();
if (c == 'Y') {
loop = false;
}
} //编写delHouse() 接受输入的id,调用Service 的del方法
public void delHouse() {
System.out.println("=====================添加房屋=====================");
System.out.print("请输入待删除房屋的编号(-1退出):");
int delId = Utility.readInt();
if (delId == -1) {
System.out.println("=====================放弃删除房屋信息=====================");
return;
}
//注意该方法本身就有循环判断的逻辑,必须输入Y/N
char choice = Utility.readConfirmSelection();
if (choice == 'Y') {//真的删除
if (houseService.del(delId)) {
System.out.println("=====================删除房屋信息成功=====================");
} else {
System.out.println("=====================房屋编号不存在,删除房屋信息失败=====================");
}
} else {
System.out.println("=====================放弃删除房屋信息=====================");
} } //编写addHouse()接受输入,创建House对象,调用add方法
public void addHouse() {
System.out.println("=====================添加房屋=====================");
System.out.print("姓名:");
String name = Utility.readString(8);
System.out.print("电话:");
String phone = Utility.readString(12);
System.out.print("地址:");
String address = Utility.readString(16);
System.out.print("月租:");
int rent = Utility.readInt();
System.out.print("状态:");
String state = Utility.readString(3);
//创建一个新的House对象,注意id 是系统分配的,
House newHouse = new House(0, name, phone, address, rent, state);
if (houseService.add(newHouse)) {
System.out.println("=====================添加房屋成功=====================");
} else {
System.out.println("=====================添加房屋失败=====================");
} } //编写listHouse()显示房屋列表
public void listHouse() {
System.out.println("=====================房屋列表=====================");
System.out.println("编号\t\t房主\t\t电话\t\t地址\t\t月租\t\t状态(未出租/已出租)");
House[] houses = houseService.list();//得到所有房屋信息
for (int i = 0; i < houses.length; i++) {
if (houses[i] == null) {//如果为空,就不需要再显示
break;
}
System.out.println(houses[i]);
}
System.out.println("=====================房屋列表显示完毕=====================");
} //显示一个主菜单
public void mainMenu() {
do {
System.out.println("\n=====================房屋出租系统=====================");
System.out.println("\t\t\t1 新 增 房 源");
System.out.println("\t\t\t2 查 找 房 屋");
System.out.println("\t\t\t3 删 除 房 屋 信 息");
System.out.println("\t\t\t4 修 改 房 屋 信 息");
System.out.println("\t\t\t5 房 屋 列 表");
System.out.println("\t\t\t6 退 出");
System.out.print("请输入你的选择(1 - 6)");
key = Utility.readChar();
switch (key) {
case '1':
addHouse();
break;
case '2':
findHouse();
break;
case '3':
delHouse();
break;
case '4':
update();
break;
case '5':
listHouse();
break;
case '6':
exit();
break;
}
} while (loop);
}
}

Chapter09 项目的更多相关文章

  1. 《Gradle权威指南》--Android Gradle多项目构建

    No1: Android多项目设置 目录结构: MyProject/ setting.gradle app/ build.gradle libraries/ lib1/ build.gradle li ...

  2. Fis3前端工程化之项目实战

    Fis3项目 项目目录结构: E:. │ .gitignore │ fis-conf.js │ index.html │ package.json │ README.md │ ├─material │ ...

  3. 【原】Android热更新开源项目Tinker源码解析系列之三:so热更新

    本系列将从以下三个方面对Tinker进行源码解析: Android热更新开源项目Tinker源码解析系列之一:Dex热更新 Android热更新开源项目Tinker源码解析系列之二:资源文件热更新 A ...

  4. 最近帮客户实施的基于SQL Server AlwaysOn跨机房切换项目

    最近帮客户实施的基于SQL Server AlwaysOn跨机房切换项目 最近一个来自重庆的客户找到走起君,客户的业务是做移动互联网支付,是微信支付收单渠道合作伙伴,数据库里存储的是支付流水和交易流水 ...

  5. Hangfire项目实践分享

    Hangfire项目实践分享 目录 Hangfire项目实践分享 目录 什么是Hangfire Hangfire基础 基于队列的任务处理(Fire-and-forget jobs) 延迟任务执行(De ...

  6. Travis CI用来持续集成你的项目

    这里持续集成基于GitHub搭建的博客为项目 工具: zqz@ubuntu:~$ node --version v4.2.6 zqz@ubuntu:~$ git --version git versi ...

  7. 【原】Android热更新开源项目Tinker源码解析系列之一:Dex热更新

    [原]Android热更新开源项目Tinker源码解析系列之一:Dex热更新 Tinker是微信的第一个开源项目,主要用于安卓应用bug的热修复和功能的迭代. Tinker github地址:http ...

  8. 【原】Android热更新开源项目Tinker源码解析系列之二:资源文件热更新

    上一篇文章介绍了Dex文件的热更新流程,本文将会分析Tinker中对资源文件的热更新流程. 同Dex,资源文件的热更新同样包括三个部分:资源补丁生成,资源补丁合成及资源补丁加载. 本系列将从以下三个方 ...

  9. Angular企业级开发(5)-项目框架搭建

    1.AngularJS Seed项目目录结构 AngularJS官方网站提供了一个angular-phonecat项目,另外一个就是Angular-Seed项目.所以大多数团队会基于Angular-S ...

随机推荐

  1. python 定义函数关键字def 简单介绍

    一  在类中定义的def # python中def 是用来干什么的? # 可以定义函数,就是定义一个功能. class People(): def __init__(self): print(&quo ...

  2. plsql 存储过程 介绍。

    /* 7-22 知识总结? 1. 存储过程 2.函数 3.包 */ /*1.什么是存储过程? 语法? 存储过程:类似于Java中的方法:完成一个特定的功能,一系列代码 (增删改操作和一些逻辑判断,se ...

  3. 「JOISC 2014 Day1」巴士走读

    「JOISC 2014 Day1」巴士走读 将询问离线下来. 从终点出发到起点. 由于在每个点(除了终点)的时间被过来的边固定,因此如果一个点不被新的边更新,是不会发生变化的. 因此可以按照时间顺序, ...

  4. 「BalkanOI 2018 Day1」Minmaxtree

    「BalkanOI 2018 Day1」Minmaxtree 每个点都有一个最大和最小权值的限制. 然后每一个权值的限制都必须要取到. 每个点显然可以直接让他取到最大或最小权值. 可以想到每个点匹配一 ...

  5. JAVA类加载器二 通过类加载器读取资源文件

    感谢原文作者:不将就! 原文链接:https://www.cnblogs.com/byron0918/p/5770684.html 一.getResourceAsStream方法 getResourc ...

  6. JAVA char类型

    char类型表示的是单个字符类型,任何数据使用单引号括起来的都是表示字符.字符只能有一个字符. 注意:特殊字符的转义序列:转义字符 转义字符的概述: 特殊字符使用"\"把其转化成字 ...

  7. IO复习

    /* 字节流 输入字节流: ---------| InputStream 所有输入字节流的基类. 抽象类 ------------| FileInputStream 读取文件的输入字节流 ------ ...

  8. 关于CSP-S2019的一篇游记

    怎么讲呢? Day1:7:00左右从家里出发,准备还是做得比较充分,早饭也记得吃了.路上闭目养神了一会儿,7:50左右到了大门附近,和大家再次把一些自认为还是比较重要的数据结构之类的再复习了一下.进去 ...

  9. 巧用python进行接口自动化测试

    一.接口自动化测试的流程 1.需求分析 1.1请求(url,方法.数据) 2.挑选需要做自动化测试的接口 3.设计自动化测试用例 4.搭建自动化测试环境 5.设计自动化执行框架(报告.参数化. 用例执 ...

  10. Spark算子 - aggregate

    释义 将每个partition内元素进行聚合,然后将每个partition的聚合结果进行combine,得到最终聚合结果.最终结果允许跟原始RDD类型不同 方法签名如下: def aggregate[ ...