这个学期学了面向对象设计与分析,让做一个住宿预约管理系统,因为事情有点多,做的就比较仓促,很多功能都不完善,勉强凑合着看
思路:
- 功能:
(1) 记录订单:分为预约订房、现场订房
(2) 修改订单信息:分为更换房间、记录到达、删除订单 - 使用图形化界面显示房间信息、订单信息,通过不同的功能按钮对数据进行操作,其中房间信息、订单信息的数据存放在数据库中,通过jdbc调用。
细节:
- 记录订单就是记录每一个房客的信息和更新房间的状态,房客填写信息,根据房客想要入住的房间类型查询该类房间的信息,若有状态为“空闲”的房间就将房客安排到这个房间,若没有则订房失败。预约订房和现场订房的区别是,预约订房得到的房间状态为“预约”,而现场订房得到的房间状态为“入住”。
- 修改订单信息都是首先以房客的电话号码为根据查找到要修改的订单,之所以用电话号码为根据是因为电话号码是唯一的。更换房间需要输入想要更换的房间的房号,若该房间的状态为“空闲”,则更换成功,否则更换失败,在更换成功后需要将原来的房间状态改为“空闲”,新的房间状态改为“预定”或者“入住”,将订单中的房间改为新房间;删除订单需要再次确认一遍,确认删除后再删除该条记录,同时将该订单中的房间状态改为“空闲”;记录到达只需将订单中的房间状态改为“入住”。
完整代码如下:
import java.awt.event.*;
import java.sql.*;
import javax.swing.*;
public class Main {
public static void main(String[] args) {
HotelJFrame a = new HotelJFrame() ;
}
}
public class Room { //房间类
String type ; //房间型号
String state ; //当前房间状态
int roomNum ; //房号
double price ; //价格
Room() {}
Room(String type, int roomNum, String state, double price) {
this.type = type ;
this.roomNum = roomNum ;
this.state = state ;
this.price = price ;
}
void setState(String state) { //修改房间状态
this.state = state ;
}
double getPrice() { //返回价格
return price ;
}
int getRoomNum() { //返回房号
return roomNum ;
}
String getType() { //返回房间类型
return type ;
}
String getState() { //返回房间状态
return state ;
}
}
public class Customer { //房客类
String checkInTime ; //入住时间
String leaveTime ; //离开时间
String roomType ; //房间型号
String phone ; //电话号码
String name ; //名字
int covers ; //人数
int roomNum ; //房间号
Customer(String checkInTime, String leaveTime, String roomType, String phone, String name, int covers, int roomNum) {
this.covers = covers ;
this.roomNum = roomNum ;
this.checkInTime = checkInTime ;
this.leaveTime = leaveTime ;
this.phone = phone ;
this.name = name ;
this.roomType = roomType ;
}
int getCovers() {
return covers ;
}
int getRoomNum() {
return roomNum ;
}
String getName() {
return name ;
}
String getPhone() {
return phone ;
}
String getCheckInTime() {
return checkInTime ;
}
String getLeaveTime() {
return leaveTime ;
}
String getRoomType() {
return roomType ;
}
void setCheckInTime(int covers) {
this.covers = covers ;
}
void setRoomNum(int roomNum) {
this.roomNum = roomNum ;
}
void setCheckInTime(String checkInTime) {
this.checkInTime = checkInTime ;
}
void setLeaveTime(String leaveTime) {
this.leaveTime = leaveTime ;
}
void setPhone(String phone) {
this.phone = phone ;
}
void setname(String name) {
this.name = name ;
}
void setRoomType(String roomType) {
this.roomType = roomType ;
}
}
public class Display { //显示房间、房客信息类
Vector<Customer> customers ;
Vector<Room> rooms ;
void setCustomer() { //从数据库导入房客信息
customers = new Vector<Customer>() ;
try { Class.forName("org.apache.derby.jdbc.EmbeddedDriver") ; }
catch(Exception ee) {}
try {
Connection con = DriverManager.getConnection("jdbc:derby:data;create=false") ;
Statement sql = con.createStatement() ;
ResultSet rs = sql.executeQuery("SELECT * FROM bookingMessage ") ;
while(rs.next()) {
String name = rs.getString(1) ;
int roomNum = rs.getInt(2) ;
int cover = rs.getInt(3) ;
String phone = rs.getString(4) ;
String checkInTime = rs.getString(5) ;
String leaveTime = rs.getString(6) ;
String type = rs.getString(7) ;
Customer c = new Customer(checkInTime, leaveTime, type, phone, name, cover, roomNum) ;
customers.add(c) ;
}
con.close() ;
}
catch(Exception ee) {}
}
void setRoom() { //从数据库导入房间信息
rooms = new Vector<Room>() ;
try { Class.forName("org.apache.derby.jdbc.EmbeddedDriver") ; }
catch(Exception ee) {}
try {
Connection con = DriverManager.getConnection("jdbc:derby:data;create=false") ;
Statement sql = con.createStatement() ;
ResultSet rs = sql.executeQuery("SELECT * FROM roomInf ") ;
while(rs.next()) {
String type = rs.getString(1) ;
int roomNum = rs.getInt(2) ;
String state = rs.getString(3) ;
double price = rs.getDouble(4) ;
Room r = new Room(type, roomNum, state, price) ;
rooms.add(r) ;
}
con.close() ;
}
catch(Exception ee) {}
}
int getRoomLength() { //获得房间数量
return rooms.size() ;
}
int getCustomerLength() { //获得房客数量
return customers.size() ;
}
Room getRoom(int i) { //获得房间信息
return rooms.get(i) ;
}
Customer getCustomer(int i) { //获得房客信息
return customers.get(i) ;
}
}
public class HotelJFrame extends JFrame implements ActionListener {
JButton bookingFunction ; //预约功能
JButton arriveFunction ; //签到功能
JButton changeFunction ; //修改功能
JButton back ; //返回页面按钮
JPanel home ; //主页面
BookingPanel bookingPanel ; //预约面板
ChangePanel changePanel ; //到达面板
int flag = 0 ; //记录使用了哪一种功能
HotelJFrame() {
setLayout(null) ;
setBounds(300, 100, 800, 800) ;
setVisible(true) ;
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE) ;
bookingFunction = new JButton("记录预约") ;
bookingFunction.addActionListener(this) ;
bookingFunction.setBounds(200, 300, 150, 100);
arriveFunction = new JButton("修改信息") ;
arriveFunction.addActionListener(this) ;
arriveFunction.setBounds(450, 300, 150, 100);
back = new JButton("返回") ;
back.setBounds(100, 700, 100, 50) ;
back.addActionListener(this) ;
back.setVisible(false) ;
home = new JPanel() ;
home.setLayout(null) ;
home.setBounds(0, 0, 800, 800) ;
home.add(bookingFunction) ;
home.add(arriveFunction) ;
add(back) ;
add(home) ;
}
public void actionPerformed(ActionEvent e) {
if(e.getSource() == bookingFunction) { //点击“记录预约”进入预约功能
bookingPanel = new BookingPanel() ;
home.setVisible(false) ;
remove(home) ;
add(bookingPanel) ;
back.setVisible(true) ;
flag = 1 ;
}
if(e.getSource() == arriveFunction) { //点击“记录到达”进入签到功能
changePanel = new ChangePanel() ;
home.setVisible(false) ;
remove(home) ;
add(changePanel) ;
back.setVisible(true) ;
flag = 2 ;
}
if(e.getSource() == back) { //返回功能页面
if(flag == 1) {
bookingPanel.setVisible(false) ;
remove(bookingPanel) ; //移除填写预约面板
}
if(flag == 2) {
changePanel.setVisible(false) ; //移除到达面板
remove(changePanel) ;
}
home.setVisible(true) ;
add(home) ; //重新添加功能按钮
back.setVisible(false) ;
}
}
}
public class BookingPanel extends JPanel implements ActionListener{
JButton reservation ; //预约订房按钮
JButton walkIn ; //现场订房按钮
JButton back ; //返回页面按钮
JTextArea roomMessage ; //显示房间信息区域
Display display ; //信息类
ReserveFill fill ; //预定订房类
WalkFill walk ; //现场订房类
int flag = 0 ; //记录使用了哪一种订房方式
BookingPanel() {
setLayout(null) ;
setBounds(0, 0, 800, 800) ;
setVisible(true) ;
reservation = new JButton("预约订房") ;
reservation.addActionListener(this) ;
reservation.setBounds(200, 30, 150, 100);
walkIn = new JButton("现场订房") ;
walkIn.addActionListener(this) ;
walkIn.setBounds(450, 30, 150, 100) ;
roomMessage = new JTextArea(12, 20) ;
roomMessage.setBounds(250, 300, 300, 200) ;
back = new JButton("返回") ;
back.setBounds(600, 700, 100, 50) ;
back.addActionListener(this) ;
back.setVisible(false) ;
add(back) ;
add(walkIn) ;
add(reservation) ;
add(roomMessage) ;
setInformation() ;
}
void setInformation() { //显示出所有房间信息
display = new Display() ;
display.setRoom() ; //从数据库中读取房间信息
roomMessage.append(" 房间 房号 价格 房间状态\n") ;
for(int i=0; i<display.getRoomLength(); i++) {
Room roomInf = display.getRoom(i) ;
roomMessage.append(roomInf.getType()+" "+roomInf.getRoomNum()+" "
+roomInf.getPrice()+" "+roomInf.getState()) ;
roomMessage.append("\n") ;
}
}
public void actionPerformed(ActionEvent e) {
if(e.getSource() == reservation) {
walkIn.setVisible(false) ;
remove(walkIn) ;
reservation.setVisible(false) ; //移除功能按钮
remove(reservation) ;
fill = new ReserveFill() ;
add(fill) ; //添加填写预约信息面板
back.setVisible(true) ;
flag = 1 ;
}
if(e.getSource() == walkIn) {
walkIn.setVisible(false) ;
remove(walkIn) ;
reservation.setVisible(false) ; //移除功能按钮
remove(reservation) ;
walk = new WalkFill() ;
add(walk) ; //添加填写预约信息面板
back.setVisible(true) ;
flag = 2 ;
}
if(e.getSource() == back) { //返回功能页面
if(flag == 1) {
fill.setVisible(false) ;
remove(fill) ; //移除填写预约信息面板
}
if(flag == 2) {
walk.setVisible(false) ; //移除填写入住信息面板
remove(walk) ;
}
walkIn.setVisible(true) ;
reservation.setVisible(true) ;
add(reservation) ; //重新添加功能按钮
add(walkIn) ;
back.setVisible(false) ;
}
}
}
public class Order extends JPanel implements ActionListener{ //记录订单类
JTextField name, cover, phone, checkInTime, leaveTime, roomType ; //填写订单信息
JButton button ; //提交订单信息按钮
Box baseBox, box1, box2 ;
Connection con ;
Statement sql ;
ResultSet rs ;
Order() {
box1 = Box.createVerticalBox() ; //左边标签栏
box1.add(new JLabel("入住人姓名")) ;
box1.add(Box.createVerticalStrut(10)) ;
box1.add(new JLabel("入住人数")) ;
box1.add(Box.createVerticalStrut(10)) ;
box1.add(new JLabel("电话号码")) ;
box1.add(Box.createVerticalStrut(10)) ;
box1.add(new JLabel("入住时间")) ;
box1.add(Box.createVerticalStrut(10)) ;
box1.add(new JLabel("离开时间")) ;
box1.add(Box.createVerticalStrut(20)) ;
box1.add(new JLabel("房间型号")) ;
box2 = Box.createVerticalBox() ; //右边输入栏
box2.add(Box.createVerticalStrut(20)) ;
box2.add(name = new JTextField(30)) ;
box2.add(Box.createVerticalStrut(10)) ;
box2.add(cover = new JTextField(30)) ;
box2.add(Box.createVerticalStrut(10)) ;
box2.add(phone = new JTextField(30)) ;
box2.add(Box.createVerticalStrut(10)) ;
box2.add(checkInTime = new JTextField(30)) ;
box2.add(Box.createVerticalStrut(10)) ;
box2.add(leaveTime = new JTextField(30)) ;
box2.add(Box.createVerticalStrut(10)) ;
box2.add(roomType = new JTextField(30)) ;
box2.add(Box.createVerticalStrut(10)) ;
baseBox = Box.createHorizontalBox() ;
baseBox.add(box1) ;
baseBox.add(Box.createHorizontalStrut(10)) ;
baseBox.add(box2) ;
button = new JButton("确认") ;
button.addActionListener(this) ;
add(baseBox) ;
add(button) ;
setBounds(0, 30, 800, 300) ;
setVisible(true) ;
}
public void actionPerformed(ActionEvent e) {}
}
public class ReserveFill extends Order implements ActionListener{ //记录预定订单
public void actionPerformed(ActionEvent e) {
if(e.getSource() == button) {
try { Class.forName("org.apache.derby.jdbc.EmbeddedDriver") ; }
catch(Exception ee) {}
try {
Connection con = DriverManager.getConnection("jdbc:derby:data;create=false") ;
Statement sql = con.createStatement() ;
ResultSet rs = sql.executeQuery("SELECT * FROM roomInf WHERE type='"+roomType.getText()+"'") ;//首先从房间信息表中找符合条件的房间
boolean flag = true ; //记录是否预定成功
while(rs.next()) {
String type = rs.getString(1) ;
int number = rs.getInt(2) ;
String state = rs.getString(3) ;
if(state.equals("空闲")) { //想预定的房间类型有空房就预定
sql.executeLargeUpdate("UPDATE roomInf SET state='预定' WHERE roomNum="+number) ; //更新房间状态
sql.executeUpdate("INSERT INTO bookingMessage VALUES ('"+name.getText()+
"', "+number+", "+cover.getText()+", '"+phone.getText()+"', '"+
checkInTime.getText()+"', '"+leaveTime.getText()+"', '"+
type+"')") ; //添加预定信息到数据库中
JOptionPane.showMessageDialog(this, "预定成功!房间号:"+number+" ",null, JOptionPane.INFORMATION_MESSAGE);
flag = false ;
break ;
}
}
if(flag)
JOptionPane.showMessageDialog(this, "预定失败!",null, JOptionPane.INFORMATION_MESSAGE);
con.close() ;
}
catch(Exception ee) {}
}
}
}
public class WalkFill extends Order implements ActionListener{ //记录现场订单
public void actionPerformed(ActionEvent e) {
if(e.getSource() == button) {
try { Class.forName("org.apache.derby.jdbc.EmbeddedDriver") ; }
catch(Exception ee) {}
try {
Connection con = DriverManager.getConnection("jdbc:derby:data;create=false") ;
Statement sql = con.createStatement() ;
ResultSet rs = sql.executeQuery("SELECT * FROM roomInf WHERE type='"+roomType.getText()+"'") ;//首先从房间信息表中找符合条件的房间
boolean flag = true ; //记录是否预定成功
while(rs.next()) {
String type = rs.getString(1) ;
int number = rs.getInt(2) ;
String state = rs.getString(3) ;
if(state.equals("空闲")) { //想入住的房间类型有空房就入住
sql.executeLargeUpdate("UPDATE roomInf SET state='入住' WHERE roomNum="+number) ; //更新房间状态
sql.executeUpdate("INSERT INTO bookingMessage VALUES ('"+name.getText()+
"', "+number+", "+cover.getText()+", '"+phone.getText()+"', '"+
checkInTime.getText()+"', '"+leaveTime.getText()+"', '"+
type+"')") ; //添加入住信息到数据库中
JOptionPane.showMessageDialog(this, "入住成功!房间号:"+number+" ",null, JOptionPane.INFORMATION_MESSAGE);
flag = false ;
break ;
}
}
if(flag)
JOptionPane.showMessageDialog(this, "入住失败!",null, JOptionPane.INFORMATION_MESSAGE);
con.close() ;
}
catch(Exception ee) {}
}
}
}
public class ChangePanel extends JPanel implements ActionListener{
JLabel label ;
JTextField phone ;
JButton arrive ; //记录到达
JButton cancel ; //删除订单
JButton transfer ; //换房间
JTextArea customerMessage ; //显示房间信息区域
JTextArea roomMessage ; //显示房间信息区域
Display display ; //信息类
ChangePanel() {
setLayout(null) ;
setBounds(0, 0, 800, 800) ;
setVisible(true) ;
label = new JLabel("请输入电话号码") ;
label.setBounds(100, 60, 100, 50) ;
phone = new JTextField(30) ;
phone.setBounds(210, 70, 400, 30) ;
arrive = new JButton("记录到达") ;
arrive.setBounds(200, 120, 100, 45) ;
arrive.addActionListener(this) ;
cancel = new JButton("删除订单") ;
cancel.setBounds(350, 120, 100, 45) ;
cancel.addActionListener(this) ;
transfer = new JButton("更换房间") ;
transfer.setBounds(500, 120, 100, 45) ;
transfer.addActionListener(this) ;
customerMessage = new JTextArea(12, 20) ;
customerMessage.setBounds(150, 200, 500, 200) ;
roomMessage = new JTextArea(12, 20) ;
roomMessage.setBounds(150, 450, 500, 200) ;
add(label) ;
add(phone) ;
add(arrive) ;
add(cancel) ;
add(transfer) ;
add(customerMessage) ;
add(roomMessage) ;
setCustomerInf() ;
setRoomInf() ;
}
void setCustomerInf() { //显示出所有房客订单信息
display = new Display() ;
display.setCustomer() ; //从数据库中读取房客订单信息
customerMessage.append("姓名 房间 房号 入住人数 电话号码 入住时间 离开时间\n") ;
for(int i=0; i<display.getCustomerLength(); i++) {
Customer customerInf = display.getCustomer(i) ;
customerMessage.append(customerInf.getName()+" "+customerInf.getRoomType()+" "
+customerInf.getRoomNum()+" "+customerInf.getCovers()+" "
+customerInf.getPhone()+" "+customerInf.getCheckInTime()+" "
+customerInf.getLeaveTime()) ;
customerMessage.append("\n") ;
}
}
void setRoomInf() { //显示出所有房间信息
display = new Display() ;
display.setRoom() ; //从数据库中读取房间信息
roomMessage.append(" 房间 房号 价格 房间状态\n") ;
for(int i=0; i<display.getRoomLength(); i++) {
Room roomInf = display.getRoom(i) ;
roomMessage.append(roomInf.getType()+" "+roomInf.getRoomNum()+" "
+roomInf.getPrice()+" "+roomInf.getState()) ;
roomMessage.append("\n") ;
}
}
public void actionPerformed(ActionEvent e) {
if(e.getSource() == arrive) { //预约者记录到达
SignIn signIn = new SignIn(phone.getText()) ;
customerMessage.setText(""); //更新信息
roomMessage.setText("") ;
setCustomerInf() ;
setRoomInf() ;
}
if(e.getSource() == cancel) { //删除订单
Cancel cancel = new Cancel(phone.getText()) ;
customerMessage.setText(""); //更新信息
roomMessage.setText("") ;
setCustomerInf() ;
setRoomInf() ;
}
if(e.getSource() == transfer) { //更换房间
int newRoom = Integer.parseInt(JOptionPane.showInputDialog(this,
"请输入要更换的房号", null, JOptionPane.INFORMATION_MESSAGE)) ;
Change change = new Change(phone.getText(), newRoom) ;
customerMessage.setText(""); //更新信息
roomMessage.setText("") ;
setCustomerInf() ;
setRoomInf() ;
}
}
}
public class Change {
Connection con ;
Statement sql ;
ResultSet rs ;
Change(String phone, int number) {
transfer(phone, number) ;
}
void transfer(String search, int newNum) { //更新入住状态
try { Class.forName("org.apache.derby.jdbc.EmbeddedDriver") ; }
catch(Exception e) {}
try {
con = DriverManager.getConnection("jdbc:derby:data;create=false") ;
sql = con.createStatement() ;
rs = sql.executeQuery("SELECT * FROM bookingMessage WHERE phone='"+search+"'") ;//根据电话号码查找订单
rs.next() ; //跳到下一个才是筛选出的订单
String type = rs.getString(7) ; //预定房间类型
int befortNum = rs.getInt(2) ; //原来房间号
rs = sql.executeQuery("SELECT * FROM roomInf WHERE roomNum="+newNum) ;
rs.next() ;
String state = rs.getString(3) ;
if( state.equals("空闲") ) {
sql.executeLargeUpdate("UPDATE bookingMessage SET roomNum="+newNum+" WHERE roomNum="+befortNum) ;
sql.executeLargeUpdate("UPDATE roomInf SET state='空闲' WHERE roomNum="+befortNum) ; //更新原来房间状态
sql.executeLargeUpdate("UPDATE roomInf SET state='预定' WHERE roomNum="+newNum) ; //更新新房间状态
JOptionPane.showMessageDialog(new ChangePanel(), "更换成功!", null, JOptionPane.INFORMATION_MESSAGE);
}
else
JOptionPane.showMessageDialog(new ChangePanel(), "更换失败!", null, JOptionPane.INFORMATION_MESSAGE);
con.close() ;
}
catch(Exception e) {
JOptionPane.showMessageDialog(new ChangePanel(), "更换失败!", null, JOptionPane.INFORMATION_MESSAGE);
}
}
}
public class Cancel {
Connection con ;
Statement sql ;
ResultSet rs ;
Cancel(String phone) {
del(phone) ;
}
void del(String search) { //删除订单
try { Class.forName("org.apache.derby.jdbc.EmbeddedDriver") ; }
catch(Exception e) {}
try {
con = DriverManager.getConnection("jdbc:derby:data;create=false") ;
sql = con.createStatement() ;
rs = sql.executeQuery("SELECT * FROM bookingMessage WHERE phone='"+search+"'") ;//根据电话号码查找订单
rs.next() ; //跳到下一个才是筛选出的订单
int flag = JOptionPane.showConfirmDialog(new ChangePanel(), "确认删除该订单?", null, JOptionPane.YES_NO_CANCEL_OPTION) ;
if(flag == JOptionPane.YES_OPTION) {
int roomNum = rs.getInt(2) ; //从订单里获得房间号
sql.executeLargeUpdate("DELETE FROM bookingMessage WHERE phone='"+search+"'") ;
sql.executeLargeUpdate("UPDATE roomInf SET state='空闲' WHERE roomNum="+roomNum) ; //更新房间状态
JOptionPane.showMessageDialog(new ChangePanel(), "删除成功!", null, JOptionPane.INFORMATION_MESSAGE);
}
con.close() ;
}
catch(Exception e) {
System.out.print(e) ;
JOptionPane.showMessageDialog(new ChangePanel(), "删除失败!", null, JOptionPane.INFORMATION_MESSAGE);
}
}
}
public class SignIn {
Connection con ;
Statement sql ;
ResultSet rs ;
SignIn(String phone) {
sign(phone) ;
}
void sign(String search) { //更新入住状态
try { Class.forName("org.apache.derby.jdbc.EmbeddedDriver") ; }
catch(Exception e) {}
try {
con = DriverManager.getConnection("jdbc:derby:data;create=false") ;
sql = con.createStatement() ;
rs = sql.executeQuery("SELECT * FROM bookingMessage WHERE phone='"+search+"'") ;//根据电话号码查找订单
rs.next() ; //跳到下一个才是筛选出的订单
int roomNum = rs.getInt(2) ; //从订单里获得房间号
sql.executeLargeUpdate("UPDATE roomInf SET state='入住' WHERE roomNum="+roomNum) ; //更新房间状态
JOptionPane.showMessageDialog(new ChangePanel(), "入住成功!", null, JOptionPane.INFORMATION_MESSAGE);
con.close() ;
}
catch(Exception e) {
JOptionPane.showMessageDialog(new ChangePanel(), "入住失败!", null, JOptionPane.INFORMATION_MESSAGE);
}
}
}
总结:
- 把所有需要输出的客房信息、订单信息分别创建相应的类,并将其作为对象放到一个Display类里,从而可以在每个需要显示信息的地方直接调用一个Display的类即可,减少了代码的重复
- 在设计功能的时候要先把最重要的功能选出来,再以此为基础进行拓展,这样可以把一些类似的功能总结到同一个大的功能里
- 在使用数据库创建表时,表中的字段要根据客房类和订单类中的属性进行创建
- 不同的类功能需要更明确一些,不要把太多的功能都放在同一个类里实现
- 查找订单需要根据一个可以唯一确定的信息来查找,例如电话号码、身份证号等
在最开始写代码的时候比较迷,写的很混乱,但之后看了一下面向对象的课本,结合着UML,稍微有了一点感觉,突然开窍了知道怎么写,本来这样的代码有点在炼油渣的感觉,之前也做个很多类似的东西,感觉不会有什么收获,但结合学的知识之后对面向对象有了更深一点的理解,也逐渐感受到了UML中的各种图对打代码的用处和好处,所以上课学的东西都不是没用的。