HiveBrain v1.2.0
Get Started
← Back to all entries
patternpythonMinor

Simple hotel reservation system

Submitted by: @import:stackexchange-codereview··
0
Viewed 0 times
hotelsystemsimplereservation

Problem

This is a reservations software for hotel and restaurant management, allowing you to add and delete rooms, show available rooms, keep track of reservations etc. I am looking to trim my code a bit and improve upon the style since it's a little cluttered right now. I believe the use of classes will help rather than making functions upon functions and 'if else' statements. The complete copy of the code is as follows.

```
from collections import namedtuple
import datetime

Reservation = namedtuple('Reservation','room arr_date dept_date guest_name confirmation_num')

#----------global variables / lists----------#

confirmation_counter = 0
bedroom_list = []
reservation_list = []

#main function
def Anteater_BandB (file_name:str)-> None:
'''main function. reads a file named file_name'''
infile = open(file_name, 'r')
data = infile.readlines()
infile.close()
for line in data:
line = line.strip()
line_reader(line)

def line_reader(l: str) -> None:
'''takes in one line of input and calls appropriate functions'''
command = l[:2].upper()
rest_of_input = l[2:].strip()
if command == '**':
pass;
elif command == 'AB':
add_bedroom(rest_of_input)
elif command == 'BL':
display_bedroom_list()
elif command == 'PL':
print_line(rest_of_input)
elif command == 'BD':
delete_bedroom(rest_of_input)
elif command == 'NR':
new_reservation(rest_of_input)
elif command == 'RL':
display_reservation_list()
elif command == 'RD':
delete_reservation(rest_of_input)
elif command == 'RB':
reservations_by_bedroom(rest_of_input)
elif command == 'RC':
reservations_by_guest(rest_of_input)
elif command == 'LA':
list_arrivals(rest_of_input)
elif command == 'LD':
list_departures(rest_of_input)
elif command =='LF':
list_free_beds(rest_of_input)
elif command == 'LO':
list_occupied(rest_of_input)

Solution

Data structures

The most important thing in any program is the data. You always want to get good datastructures first, by understanding the data you fully understand the problem. In this case I'm concerned that you have a situation where too much of your underlying data is based on strings. You end up manipulating strings for all manner of things that would be more cleanly represented by other datastructures.

Rooms for example are probably better stored as some data structure that specifically represents a room. Same goes for guests.
Refactoring

There's a lot of code here that could be logically grouped together.

For example there's a bunch of functions that have the following structure:

def some_function(line:str):
    global bedroom_list
    #more code


Usually this is a fairly strong indication that you should be making a class that contains bedroom_list along with all those function as methods. The main reason for this is that global mutable state introduces very hard to fix bugs and makes testing very difficult. How would you unit test this code now? By refactoring in this way you have a change to make your code testable which is a huge boost to the correctness and reliability of your code. This pays large dividends later in the time that is saved from needing to debug and also allows you to have much more confidence in the quality of your code when you make changes in the future. Regressions are much easier to find when your code has good test coverage.

This is completely setting aside concurrency issues, if you do end up adding concurrency later these global mutable state will cause you much much pain and suffering.
Separation of logic and user interface

The main guiding principle with these things is that changing the UI should not ever impact your backend data processing function.
Currently you have functions that both process data AND interact with the user. From a design perspective it is much cleaner if you have the data processing as a separate step from the user input/output. This is because you don't want a situation where making a change to the UI can create problem with your data processing, by completely separating that functionality it makes it a lot easier to avoid such issues. This has the additional benefit of making it much easier to say change to a GUI in the future or some other interface.

Code Snippets

def some_function(line:str):
    global bedroom_list
    #more code

Context

StackExchange Code Review Q#101589, answer score: 3

Revisions (0)

No revisions yet.