2

Cómo simular el POS de un Restaurante con Python

Hola, ¿te gustan los retos?, a mi también, por eso te invito a que me acompañes en este tutorial para aprender entre todos un poco más!

¿Qué veremos?

  • Uso de listas
  • Uso de ciclos while y for
  • Uso del if

¿Cómo lo haremos?
Crearemos un menu simple mediante un diccionario y matrices (listas de listas), luego ingresaremos datos de usuario y mesa (validando que exista), procederemos a solicitar elegir las distintas opciones de menú, cantidades, calcularemos el subtotal de cada selección y daremos la opción de seleccionar cuantas veces se requiera mediante un ciclo while, finalmente imprimiremos el detalle de cada selección junto con el total del pedido por medio de un ciclo for.

  1. Creamos el menú mediante el uso de un diccionario, donde definimos el ID y su categoría correspondiente, se deja abierta la opción de modificar o agregar más items al menú.
menu = {'1':'Entradas',
        '2':'Platos Fuertes',
        '3':'Postres',
        '4':'Bebidas'
       }
  1. Este menú será la opción principal para cada usuario, luego de esto creamos a partir de matrices o lista de listas el detalle de cada uno de ellos con el ID, descripción y valor unitario de la siguiente manera:
entradas = [
  ['1', 'Deditos de Queso (x3)', 18000],
  ['2', 'Canasta de Mariscos', 27000],
  ['3', 'Chicharrones en Sour Cream', 30000]
]

platos_fuertes = [
  ['1', 'Fetuccini di Mare', 40000],
  ['2', 'Bondiola de Cerdo', 42000],
  ['3', 'Milanesa Provenzal', 47000]
]

postres = [
  ['1', 'Cheesecake de Frutos Rojos', 8000],
  ['2', 'Pie de Limón', 9000],
  ['3', 'Cannoli', 14000]
]

bebidas = [
  ['1', 'Soda di Solei', 10000],
  ['2', 'Soda de Fruta', 11000],
  ['3', 'Limonada de Hierbabuena', 12000]
]
  1. ¡Excelente!🎊 estamos listos para dar la bienvenida a nuestro programa mediante un print multilínea (triple comilla), dar formato por medio de >> f << y centrando la información y rellenando con el método center(), esto con la finalidad de dar una interfaz amigable al programa.
print(f'''
{"".center(50,"*")}
{" Bienvenido a TAMALU Restaurant ".center(50,"*")}
{"".center(50,"*")}''')

Se verá 👀 de la siguiente manera:

*********************************************************** Bienvenido a TAMALU Restaurant ***********************************************************
  1. A continuación solicitaremos al usuario el nombre y el número de la mesa, acá usaremos lo siguiente:
  • input(*): para que el usuario interactúe con la máquina.
  • *.tittle(): este método pone la primera letra de cada nombre en mayúscula y las demás en minúscula.
  • int(*): para convertir en entero el valor de la mesa ingresado por medio del input, ya que por defecto quedará como string.
usuario = input('''
El pedido saldrá a nombre de: ''').title()
mesa = int(input('''Ingrese el número de la mesa: '''))

Se verá 👀 de la siguiente manera:

El pedido saldrá a nombre de: Maycol Suárez
Ingrese el número dela mesa: 15
  1. En este caso asumimos que el restaurante solo tiene 20 mesas, por tanto si el usuario ingresa un valor que no se encuntre en el rango de 1-20 lo debe validar, se le mostrará un mensaje de alerta y le pediremos de nuevo el número de la mesa, finalmente si persiste el error daremos la opción de salida, acá usaremos:
  • Ciclo while: que nos valida que el número de mesa se encuentre en el rango.
  • Comparador or: usado en el while para que se cumpla una de las dos condiciones.
  • Función if: en esta ocasión la usamos para hacer una segunda validación, si el usuario ingresa nuevamente un valor erroneo le damos la posibilidad de salir presionando cualquier letra.
  • *.isalpha(): validamos que el dato ingresado sea alfabético, en este caso para salir del programa.
  • exit(): esta función nos permite salir del programa.
while mesa < 1or mesa > 20:
  print(f'''
⚠ {mesa} no es una mesa válida ⚠
''')
  mesa = int(input('''Ingrese un número de mesa válido entre 1 y 20: '''))
  if mesa < 1or mesa > 20:
    salir = input('''
Si desea salir presiones cualquier letra, de lo contrario presione enter: ''')
    if salir.isalpha() == True:
      exit()

acá 👇🏼 te dejo un ejemplo:

⚠ 25 no es una mesa válida ⚠

Ingrese un número de mesa válido entre 1 y 20: 25

Si desea salir presiones cualquier letra, de lo contrario presione enter: 

¡Listo!, ¿Estás preparado?, ¡Continuemos!

  1. Para continuar necesitamos declarar e inicializar algunas variables, el número de items, la desición de continuar (para usar en el siguiente while), la lista del _pedido _ y el total de la orden asi:
items = 0continuar = 'Y'pedido = []
total = 0
  1. El siguiente y principal bloque será un while, este le permite al usuario agregar una y otra vez la cantidad de productos que desee hasta que decida parar (Nota: en este caso no usaremos un validador que garantice que el usuario use solo las opciones Y/N, pero si quieres tu lo puedes hacer mediante un while igual a como lo hicimos con la mesa, ¡Anímate a hacerlo tu mismo!).
while continuar.upper() == 'Y':
.
.
.
.
.
	continuar = input('''
¿Desea ordenar algo más? (Y/N) ''')

Si te fijaste, usámos el método *.upper() para convertir a mayúscula la letra ingresada por el usuario, con esto es válido si continúa con Y o con y.

¡Uff! ¿Está largo verdad?, pero espera 🫷🏼, no te alcanzas a imaginar el resultado 😋

  1. Llegó la hora de mostrarle al usuario el menú:
    Para ello imprimiremos un título similar a la bienvenida, y luego de ello recorreremos el diccionario del menú mediante un for, adicional le pediremos al usuario seleccionar el submenú asi:
	print(f'''
{"M E N Ú  P R I N C I P A L".center(50,".")}
  ''')
  for submenus in menu:
    print(submenus, menu[submenus])
  
  option = input('''
Seleccione una opción: ''')

Ojo: recuerda respetar la identación (tabulación)

Desde el diccionario menu navegamos mediante el for por cada linea llamándolos submenus e imprimimos en cada ciclo una linea con el key (submenus) y el value menu[submenus] quedando visulamente así 👇🏼:

............M E N Ú  P R I N C I P A L............1 Entradas
2 Platos Fuertes
3 Postres
4 Bebidas

Seleccione una opción:
  1. Según la elección del usuario mostraremos los datos de la matríz de cada submenú, para ello usaremos if/elif/else para evaluar la elección y un for para imprimir cada submenú.
  • Una vez el usuario elija una opción válida le pediremos ingresar la cantidad (tarea: valida que se ingrese un número)
  • Luego imprimimos la cantidad, el producto seleccionado, calculamos el subtotal del producto dependiendo de la cantidad y lo imprimimos.
  • Finalmente le pedimos al usuario que confirme su elección mediante un if con opción Y/N
  • Usando el método .append() agregamos los datos seleccionados del submenú, cantidad, producto, valor unitario y valor total y con el mismo método agregar esta lista a la matriz (lista) pedido.
  • Usamos el método de incremento para items asi: items += 1
  • Cuando el usuario no desee continuar o elija una opción diferente a >Y< usaremos un while para confirmar la finalización del pedido, para esto en caso de que el usuario desee finalizar saldremos del while mediante un break.

Nota: Se usan varios print(*) para darle formato y embellecer la interfaz de usuario así como el método .center() para centrar, .rjust() para justificar a la derecha, .ljust() para justificar a la izquierda y la función de formato f.

Nota: en los submenús no se restringen las entradas del usuario, por tanto si elige una opción fuera del submenú se romperá el código, ¡es tu oportunidad!, crea una validación que limite al usuario a elegir una opción de cada submenú o finalizar la compra.

El código se repite para cada opción del menú con un elif usando la respectiva matriz y se finaliza con un else donde se imprime un mensaje de opción no valida y se continúa el flujo preguntando al usuario si desea continuar, quedando el código así:

if option == '1':											# Validación de selección de usuario
    print(f'''
{"Entradas:".ljust(50,".")}										
    ''')
    for prod_entrada in entradas:				# Ciclo for para el submenú elegido
      print(f'>> {prod_entrada[0]} - {prod_entrada[1]}')
      value_product = str(f'$ {prod_entrada[2]}')
      print(f'''{value_product.rjust(50, "-")}
      ''')
    product = int(input('''
Elija un producto: '''))								# Elección de producto del submenú
    product -= 1# Decremento en 1 para índice
    quantity = int(input('''
Ingrese la cantidad: '''))							# Cantidad del producto elegido
    subtotal = quantity * int(entradas[product][2])		# Cálculo = Cant * VUnit
    print(f'''
{"".center(50,".")}''')
    print(f'''
Entrada: {quantity} x {entradas[product][1]}''')
    subt = f'Subtotal: ${subtotal}'# Se crea la variable subt como string
    print(subt.rjust(50))
    confirmar = input('''
Confirmar (Y/N): ''')										# Confirmación de la elección if confirmar.upper() == 'Y':				# Validación de confirmación
      prod = []													# Se declara y se inicia lista
      prod.append('Entrada')						# Se agregan datos con .append()
      prod.append(quantity)
      prod.append(entradas[product][1])
      prod.append(entradas[product][2])
      prod.append(subtotal)
      pedido.append(prod)								# Se agrega elección al pedido
      items += 1# Se incrementa el item agregadoelif option == '2':										# Se repite proceso con submenú 2
		.
		.
		.
		.
  elif option == '3':										# Se repite proceso con submenú 3
		.
		.
		.
		.
  elif option == '4':										# Se repite proceso con submenú 4
		.
		.
		.
		.
	else:																	# Se envía alerta de ingreso errado
    print(f'''
⚠ {option} no es una opción válida ⚠
''')

  continuar = input('''
¿Desea ordenar algo más? (Y/N) ''')

  while continuar.upper() != 'Y':
    finalizar = input('''
¿Desea finalizar el pedido? (Y/N) ''')
    if finalizar.upper() != 'Y':
      continuar = 'Y'else:
      break

Se verá 👀 de la siguiente manera:

Platos Fuertes:...................................
        
>> 1 - Fetuccini di Mare
-------------------------------------------$ 40000
      
>> 2 - Bondiola de Cerdo
-------------------------------------------$ 42000
      
>> 3 - Milanesa Provenzal
-------------------------------------------$ 47000
      

Elija un producto: 2

Ingrese la cantidad: 2..................................................

Plato Fuerte: 2 x Bondiola de Cerdo
                                  Subtotal: $84000

Confirmar (Y/N): y

¿Desea ordenar algo más? (Y/N)  n

¿Desea finalizar el pedido? (Y/N) y

¿Cómo te ha parecido hasta ahora? 😀😔😡😭, ¿Ya corriste tu código?
¡Prepárate para finalizar este tutorial imprimiendo cada detalle del pedido almacenado en la matriz (lista de listas) pedido y el total del mismo! ¡Vámos!

  1. ¡Es hora de terminar!, para ello usaremos un if para validar si hay por lo menos un producto agregado al pedido, luego imprimimos el usuario y la mesa con un formato similar a la bienvenida, seguido de ello vamos a imprimir el submenú, cantidad, producto, valor unitario y subtotal para cada línea, esto por medio de un for, el cuál nos permitirá recorrer fila a fila por medio de la variable i inicializada antes del for en 0 e incrementada tras cada impresión de linea dentro del for.
    Para imprimir cada dato de la matriz en cada línea usamos los subíndices de fila y columna, sabiendo que i me da la fila y el número de columna lo da el orden en que fueron guardados previamente; el valor total lo calculamos mediante la suma incremental del subtotal como entero de cada producto seleccionado en cada ciclo del for, finalmente cerramos con un agradecimiento y despedida, terminando nuestro código de la siguiente manera 👇🏼:
if items > 0:
  print(f'''

{"".center(50,"*")}''')
  print(f''' Resumen Pedido Mesa: {mesa} '''.center(50,"*"))
  print(f''' Usuario: {usuario} '''.center(50,"*"))
  print(f'''{"".center(50,"*")}
  ''')
  i = 0for row in pedido:
    print(f'''{pedido[i][0]}
    {pedido[i][1]} x {pedido[i][2]} (${pedido[i][3]})''')  
    subt = f'Subtotal: ${pedido[i][4]}'
    print(subt.rjust(50))
    total = total + int(pedido[i][4])
    i += 1
  print(f'''
{"".center(50,"*")}
Total a Pagar
''' + f'${total}'.rjust(50))
print(f'''{"".center(50,"*")}''')  
  
print(f'''
{" ¡Gracias por su visita, vuelva pronto! ".center(50,"*")}
''')

Finalmente tendremos un cierre de la siguiente manera 👀:

************************************************************** Resumen Pedido Mesa: 15 ************************** Usuario: Maycol Suárez ***************************************************************
  
Plato Fuerte
    2 x Fetuccini di Mare ($40000)
                                  Subtotal: $80000
Plato Fuerte
    2 x Bondiola de Cerdo ($42000)
                                  Subtotal: $84000
Bebida
    3 x Limonada de Hierbabuena ($12000)
                                  Subtotal: $36000

**************************************************
Total a Pagar
                                           $200000
******************************************************* ¡Gracias por su visita, vuelva pronto! *****

Doy primeramente gracias a Dios por permitirme compartir con ustedes lo aprendido en este curso, a Platzi y al profesor Nicolas por su dedicación, a mi amada empresa Rappi, quien nos brinda las oportunidades de crecer y a ustedes compañeros por llegar hasta acá y querer seguir aprendiendo conmigo, les agradezco su feedback!!! Maycol 😉🤙🏼

Escribe tu comentario
+ 2
1
2982Puntos
2 meses

Está genial Maycol! Gracias por compartilo!!