사이먼's 코딩노트
[Java] 호텔 예약 관리 프로그램 제작(7) 본문
[호텔 예약 관리 프로그램 제작]
- 작성된 모든 코드는 저의 깃허브 리포지터리에서 확인하실 수 있습니다.
- 깃허브 리포지터리 주소 : https://github.com/psm817/hotel_booking_proj
[예약 취소 구현]
- 이번에는 객실 예약을 한 사용자가 본인의 예약 건을 취소하기 위한 'booking delete' 를 구현해보고자 한다.
- 예약과 관련된 기능들은 모두 BookingController.java 클래스에 코드를 추가하였다.
package org.example.controller;
import org.example.Util;
import org.example.dto.Booking;
import org.example.dto.Room;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
public class BookingController extends Controller {
private Scanner sc;
private String cmd;
public static List<Booking> bookings;
public Room bookingAbleRoom;
public BookingController() {
sc = new Scanner(System.in);
bookings = new ArrayList<>();
}
public void doAction(String cmd, String actionMethodName) {
this.cmd = cmd;
switch(actionMethodName) {
case "room" :
doBooking();
break;
case "check" :
doCheckBooking();
break;
case "delete" :
doDeleteBooking();
break;
default :
System.out.println("존재하지 않는 서비스입니다.");
break;
}
}
public void doDeleteBooking() {
int foundBookingCount = getBookingsByName(loginedGuest.name);
System.out.printf("%s 님, 총 [%d]건의 예약이 있습니다.\n", loginedGuest.name, foundBookingCount);
if(foundBookingCount == 0) {
System.out.println("취소하실 예약 건이 없습니다.");
}
else {
System.out.printf("==== [%s 님] 예약 현황 =======\n", loginedGuest.name);
System.out.println("예약번호 | 호수 | 예약날짜");
for (int i = 0; i < bookings.size(); i++) {
Booking bookedAllRoom = bookings.get(i);
for(int j = 0; j < rooms.size(); j++) {
Room foundAllRoom = rooms.get(j);
int roomId = foundAllRoom.floor * 100 + foundAllRoom.id;
if(bookedAllRoom.regDate.equals(foundAllRoom.bookingDate) && bookedAllRoom.roomId == roomId && loginedGuest.name.equals(bookedAllRoom.guestName)) {
System.out.printf(" %4d | %d | %s\n", bookedAllRoom.id, bookedAllRoom.roomId, bookedAllRoom.regDate);
}
}
}
System.out.println("====================================");
System.out.print("예약을 취소하시겠습니까?) ");
String answer = sc.nextLine();
Booking foundBooking = foundBookedRoomByName(loginedGuest.name);
Room foundRoom = getRoomsByNum(foundBooking.roomId);
if(answer.equals("yes")) {
System.out.print("취소하시고 싶은 예약번호를 입력(숫자만) : ");
int answerId = sc.nextInt();
sc.nextLine();
if(answerId == foundBooking.id) {
bookings.remove(foundBooking);
foundRoom.bookingDate = null;
foundRoom.booked = "예약가능";
System.out.println("예약이 취소되었습니다!!");
}
}
else if(answer.equals("no")) {
System.out.println("예약취소를 중단합니다.");
}
else {
System.out.println("\'yes\' 또는 \'no\'를 입력해주세요");
}
}
}
public Room getRoomsByNum(int roomNum) {
int index = getRoomsIndexByNum(roomNum);
if(index != -1) {
return rooms.get(index);
}
return null;
}
public int getRoomsIndexByNum(int roomNum) {
int i = 0;
for(Room room : rooms) {
if((room.floor * 100 + room.id) == roomNum) {
return i;
}
i++;
}
return -1;
}
private int getBookingsByName(String name) {
int sum = 0;
for(Booking booking : bookings) {
if(booking.guestName.equals(name)) {
sum++;
}
}
return sum;
}
private Booking foundBookedRoomByName(String name) {
int i = 0;
for(Booking booking : bookings) {
if(booking.guestName.equals(name)) {
return bookings.get(i);
}
i++;
}
return null;
}
}
- 먼저 서비스 명령어를 구분하기 위해 doAction() 메서드에서 'delete' 라는 문자열을 통해 doDeleteBooking() 메서드를 호출하도록 한다.
- 예약 취소는 로그인이 된 회원에 한해서만 취소가 가능하고, 회원은 본인이 예약한 내역을 먼저 볼 수 있다.
- doDeleteBooking() 메서드가 호출됨과 동시에 총 몇 건의 예약이 있는지 확인이 가능하다.
- 만약 예약한 이력이 없다면 취소할 예약 건이 없다는 안내와 함께 해당 서비스가 종료된다.
- 그렇지 않다면 booking check와 마찬가지로 조건문을 통해 예약한 날짜와 객실번호가 모두 일치하면 자동으로 로그인 된 회원의 모든 예약 현황을 보여준다.
- 그 다음, 예약을 취소하겠냐는 질문이 나오게 되고 만약 취소를 원한다면 해당 예약 건의 예약번호를 입력한다.
- 여기서 말하는 예약번호는 bookings에 하나씩 쌓이는 고유 id를 뜻한다.
- 만약 사용자가 입력한 예약번호와 foundBookedRoomByName() 메서드를 통해 가져온 예약의 정보의 id와 일치한다면 예약이 취소되었다는 안내와 함께 기존에 예약했던 날짜에 해당하는 객실의 예약여부를 '예약가능' 으로 변경하고 예약된 날짜인 bookingDate를 null 값으로 채워준다.
- 추가로 bookings 리스트에 저장된 해당 예약 건을 remove() 를 이용하여 삭제한다.
- 해당 작업을 하는 이유는 해당 회원이 예약을 취소하게 되면 다른 회원들이 객실 예약을 할 수 있게끔 하기 위해서다.
- 무한루프를 사용하여 만약 사용자가 예약 취소를 원하지 않는다면 해당 메서드를 종료하고, yes나 no가 아닌 다른 대답을 했다면 대답이 잘못되었다는 안내와 함께 다시 예약 취소를 원하는 지 질문한다.
[문제점 개선]
- 현재 상태에서 프로그램을 실행했을 때, 각 회원이 오직 하나의 예약을 했다고 가정한다면 각 회원의 예약 취소 기능은 문제없이 동작한다.
- 하지만 2개 이상의 예약을 했다면 예약 취소 시 원하는 예약번호에 맞춰 예약 건이 취소되지 않고 무조건 첫번째 예약 건이 삭제된다.
- 위 문제는 예약을 취소하고자 하는 객실을 반복문을 통해 가져오는 과정에서 조건문을 통해 무조건 예약 번호만 같다면 삭제가 되도록 구현했기 때문이다.
- 해당 문제를 개선하기 위해 약간의 코드를 수정하였다.
public void doDeleteBooking() {
int foundBookingCount = getBookingsByName(loginedGuest.name);
System.out.printf("%s 님, 총 [%d]건의 예약이 있습니다.\n", loginedGuest.name, foundBookingCount);
if(foundBookingCount == 0) {
System.out.println("취소하실 예약 건이 없습니다.");
}
else {
System.out.printf("==== [%s 님] 예약 현황 =======\n", loginedGuest.name);
System.out.println("예약번호 | 호수 | 예약날짜");
for (int i = 0; i < bookings.size(); i++) {
Booking bookedAllRoom = bookings.get(i);
for(int j = 0; j < rooms.size(); j++) {
Room foundAllRoom = rooms.get(j);
int roomId = foundAllRoom.floor * 100 + foundAllRoom.id;
if(bookedAllRoom.regDate.equals(foundAllRoom.bookingDate) && bookedAllRoom.roomId == roomId && loginedGuest.name.equals(bookedAllRoom.guestName)) {
System.out.printf(" %4d | %d | %s\n", bookedAllRoom.id, bookedAllRoom.roomId, bookedAllRoom.regDate);
}
}
}
System.out.println("====================================");
System.out.print("예약을 취소하시겠습니까?) ");
String answer = sc.nextLine();
if(answer.equals("yes")) {
System.out.print("취소하시고 싶은 예약번호를 입력(숫자만) : ");
int answerId = sc.nextInt();
sc.nextLine();
for(int i = 0; i < bookings.size(); i++) {
Booking bookedAllRoom = bookings.get(i);
for(int j = 0; j < rooms.size(); j++) {
Room foundAllRoom = rooms.get(j);
int roomId = foundAllRoom.floor * 100 + foundAllRoom.id;
if(bookedAllRoom.regDate.equals(foundAllRoom.bookingDate) && bookedAllRoom.roomId == roomId && loginedGuest.name.equals(bookedAllRoom.guestName)) {
if(bookedAllRoom.id == answerId) {
bookings.remove(bookedAllRoom);
foundAllRoom.bookingDate = null;
foundAllRoom.booked = "예약가능";
System.out.println("예약이 취소되었습니다!!");
}
}
}
}
}
else if(answer.equals("no")) {
System.out.println("예약취소를 중단합니다.");
}
else {
System.out.println("\'yes\' 또는 \'no\'를 입력해주세요");
}
}
}
- 2개 이상의 예약 건이 있을 경우를 생각하여 취소하고 싶은 예약번호를 회원이 입력한 후에 이중 반복문을 사용하여 bookedAllRoom과 foundAllRoom 변수를 통해 전체 예약 건과 객실을 하나씩 살핀다.
- 이 때 객실번호를 추출하기 위해서 foundAllRoom의 층을 나타내는 floor에 100을 곱한 후, 호수인 id를 더하여 roomId 변수를 하나 선언한다.
- 그리고 조건문을 통해 예약날짜와 객실 번호, 예약자 이름이 모두 같다는 조건을 두어 원하는 예약번호를 입력했을 때 삭제 가능하도록 한다.
반응형
'프로젝트 > [Java] 호텔 예약 관리 프로그램 제작' 카테고리의 다른 글
[Java] 호텔 예약 관리 프로그램 제작(9) (0) | 2024.04.17 |
---|---|
[Java] 호텔 예약 관리 프로그램 제작(8) (0) | 2024.04.17 |
[Java] 호텔 예약 관리 프로그램 제작(6) (0) | 2024.04.17 |
[Java] 호텔 예약 관리 프로그램 제작(5) (0) | 2024.04.16 |
[Java] 호텔 예약 관리 프로그램 제작(4) (0) | 2024.04.16 |