Progettazione di soluzioni di ricerca operativa: un’applicazione di routing intuitiva con Streamlit |  di Bruno Scalia CF Leite |  Settembre 2023

 | Intelligenza-Artificiale

Come descritto in precedenza, possiamo definire le impostazioni generali di Streamlit nel file config.toml file all’interno del .streamlit cartella. Nell’esempio TSP, l’ho usato per definire colori e caratteri. Questo è una specie di layout viola chiaro, ma puoi provare diversi colori. Assicurati solo di definirli Codici colore esadecimali.

(theme)
primaryColor = "#5300A5"
backgroundColor = "#403E43"
secondaryBackgroundColor = "#1C1B1E"
textColor = "#F5F3F7"
font = "sans serif"
base = "dark"

Cominciamo a riempire il contenuto di app.py con le importazioni Python. Il pacchetto os verrà utilizzato per gestire i percorsi dei file nel nostro sistema operativo; ByteIO verrà utilizzato per emulare un file di output scaricabile mantenuto in memoria anziché su disco; json verrà utilizzato per serializzare la nostra soluzione di output; Elenco è solo un suggerimento.

Per lavorare con i dataframe, panda sarà usato; il risolutore Alti è importato da Piomo per risolvere il nostro problema (in caso di MIP); illuminato è la base dell’interfaccia; E streamlit_folium verrà utilizzato per inserire a foglia Mappa nell’app. Vengono importate anche le funzioni personalizzate aggiuntive definite nel pacchetto interno.

import os
from io import BytesIO
import json
from typing import List

import pandas as pd
from pyomo.contrib.appsi.solvers.highs import Highs
import streamlit as st
from streamlit_folium import st_folium

from optimize.tsp import get_distance_xy, build_mip, solve_mip, TSP, plot_tour, request_matrix,\
plot_map, get_coord_path

IL session_state gli attributi memorizzeranno il file tour di una soluzione attuale, il panda dataframe di un dato file di input, il valore di quella soluzione e il percorso delle coordinate del percorso (ottenuto da OpenStreetMap).

# Create current solution as session_state
if "tour" not in st.session_state:
st.session_state.tour = None

if "dataframe" not in st.session_state:
st.session_state.dataframe = None

if "sol" not in st.session_state:
st.session_state.sol = None

if "route_path" not in st.session_state:
st.session_state.route_path = None

Alcune delle funzioni di utilità utilizzate sono:

  • driving_distances: per ottenere la matrice delle distanze da OpenStreetMap è stato fornito un dataframe (importante per memorizzare qui i risultati).
  • upload_callback: reimposta session_state attributi quando viene caricato un nuovo file di input.
  • update_path: dato un tour, ottiene le coordinate della mappa del percorso di guida corrispondente per tracciare i risultati.
# Finds distance matrix
@st.cache
def driving_distances(dataframe: pd.DataFrame):
return request_matrix(dataframe)("distances") / 1000

# Callback uploading a new file
def upload_callback():
st.session_state.tour = None
st.session_state.sol = None
st.session_state.route_path = None

# Update route path after solution
def update_path(tour: List(int), dataframe: pd.DataFrame):
coord_rt = dataframe.loc(tour, :)
path = get_coord_path(coord_rt)
st.session_state.route_path = path

E poi configuriamo il layout della pagina. Nello script seguente includiamo un’icona e un titolo per la pagina web; quindi inseriamo la stessa icona nella barra laterale e scriviamo un’introduzione in stile markdown. Ti suggerisco di scappare streamlit run app.py e controllare i risultati finora.

# Path to icon
icon_path = os.path.join("assets", "icon_tsp.png")

# Set the page config to wide mode
st.set_page_config(
page_title="TSP",
page_icon=icon_path,
layout="wide",
)

st.sidebar.image(icon_path)

st.title("TSP")
st.write("Welcome to the Traveling Salesman Problem solver.")

Una delle funzioni di utilità che ho definito legge il contenuto dal file README.md file e visualizzare questo contenuto se l’utente seleziona questa opzione. Poiché voglio mantenere il condizionale per visualizzare il contenuto indipendentemente da una possibile riesecuzione, ho utilizzato a casella di selezione invece di a pulsante fare così.

display_tutorial = st.checkbox("Display tutorial")
if display_tutorial:
section = st.selectbox("Choose a section", ("Execution", "Solutions", "Contact"), index=1)
tutorial = read_section(section)
st.markdown(tutorial)

E poi definiamo i parametri del risolutore e carichiamo un file di input…

Fonte: towardsdatascience.com

Lascia un commento

Il tuo indirizzo email non sarà pubblicato. I campi obbligatori sono contrassegnati *