1. Panoramica
In questo lab imparerai a utilizzare Vertex AI Workbench per l'esplorazione dei dati e l'addestramento di modelli ML.
Cosa imparerai
Al termine del corso sarai in grado di:
- Crea e configura un'istanza di Vertex AI Workbench
- Utilizzare il connettore BigQuery di Vertex AI Workbench
- Addestra un modello su un kernel Vertex AI Workbench
Il costo totale per eseguire questo lab su Google Cloud è di circa 1$.
2. Introduzione a Vertex AI
Questo lab utilizza la più recente offerta di prodotti AI disponibile su Google Cloud. Vertex AI integra le offerte ML di Google Cloud in un'esperienza di sviluppo fluida. In precedenza, i modelli addestrati con AutoML e i modelli personalizzati erano accessibili tramite servizi separati. La nuova offerta combina entrambi in un'unica API, insieme ad altri nuovi prodotti. Puoi anche migrare progetti esistenti su Vertex AI.
Vertex AI include molti prodotti diversi per supportare i flussi di lavoro ML end-to-end. Questo lab si concentrerà su Vertex AI Workbench.
Vertex AI Workbench aiuta gli utenti a creare rapidamente workflow end-to-end basati su notebook grazie all'integrazione profonda con i servizi di dati (come Dataproc, Dataflow, BigQuery e Dataplex) e Vertex AI. Consente ai data scientist di connettersi ai servizi di dati GCP, analizzare i set di dati, sperimentare diverse tecniche di modellazione, eseguire il deployment dei modelli addestrati in produzione e gestire MLOps durante il ciclo di vita del modello.
3. Panoramica del caso d'uso
In questo lab esplorerai il set di dati London Bicycles Hire. Questi dati contengono informazioni sui viaggi in bicicletta del programma pubblico di bike sharing di Londra dal 2011. Inizierai esplorando questo set di dati in BigQuery tramite il connettore BigQuery di Vertex AI Workbench. Dopodiché, caricherai i dati in un blocco note Jupyter utilizzando pandas e addestrerai un modello TensorFlow per prevedere la durata di un viaggio in bicicletta in base a quando si è verificato il viaggio e alla distanza percorsa in bicicletta.
Questo lab utilizza i livelli di pre-elaborazione Keras per trasformare e preparare i dati di input per l'addestramento del modello. Questa API ti consente di incorporare la pre-elaborazione direttamente nel grafico del modello TensorFlow, riducendo il rischio di asimmetria tra addestramento e pubblicazione garantendo che i dati di addestramento e di pubblicazione vengano sottoposti a trasformazioni identiche. Tieni presente che a partire da TensorFlow 2.6, questa API è stabile. Se utilizzi una versione precedente di TensorFlow, devi importare il simbolo sperimentale.
4. Configura l'ambiente
Per eseguire questo codelab, devi avere un progetto Google Cloud Platform con la fatturazione abilitata. Per creare un progetto, segui le istruzioni riportate qui.
Passaggio 1: abilita l'API Compute Engine
Vai a Compute Engine e seleziona Abilita se non è già abilitato.
Passaggio 2: attiva l'API Vertex AI
Accedi alla sezione Vertex AI della tua console Cloud e fai clic su Abilita API Vertex AI.

Passaggio 3: crea un'istanza di Vertex AI Workbench
Nella sezione Vertex AI della console Cloud, fai clic su Workbench:

Abilita l'API Notebooks, se non l'hai ancora fatto.

Una volta attivata, fai clic su BLOCCHI NOTE GESTITI:

Poi seleziona NUOVO QUADERNO.

Assegna un nome al notebook e, in Autorizzazione, seleziona Service account.

Seleziona Impostazioni avanzate.
Nella sezione Sicurezza, seleziona "Abilita terminale" se non è già abilitata.

Puoi lasciare invariate tutte le altre impostazioni avanzate.
Quindi, fai clic su Crea.
Una volta creata l'istanza, seleziona APRI JUPYTERLAB.

5. Esplora il set di dati in BigQuery
Nell'istanza di Vertex AI Workbench, vai sul lato sinistro e fai clic sul connettore BigQuery in Notebooks.

Il connettore BigQuery ti consente di esplorare ed eseguire query facilmente sui set di dati BigQuery. Oltre ai set di dati nel tuo progetto, puoi esplorare i set di dati in altri progetti facendo clic sul pulsante Aggiungi progetto.

Per questo lab, utilizzerai i dati dei set di dati pubblici di BigQuery. Scorri verso il basso fino a trovare il set di dati london_bicycles. Vedrai che questo set di dati ha due tabelle, cycle_hire e cycle_stations. Esploriamoli uno alla volta.

Innanzitutto, fai doppio clic sulla tabella cycle_hire. Vedrai che la tabella si apre come nuova scheda con lo schema della tabella e i metadati, come il numero di righe e le dimensioni.

Se fai clic sulla scheda Anteprima, potrai visualizzare un campione dei dati. Eseguiamo una semplice query per vedere quali sono i percorsi più popolari. Innanzitutto, fai clic sul pulsante Tabella query.

Poi, incolla il seguente codice nell'editor SQL e fai clic su Invia query.
SELECT
start_station_name,
end_station_name,
IF(start_station_name = end_station_name,
TRUE,
FALSE) same_station,
AVG(duration) AS avg_duration,
COUNT(*) AS total_rides
FROM
`bigquery-public-data.london_bicycles.cycle_hire`
GROUP BY
start_station_name,
end_station_name,
same_station
ORDER BY
total_rides DESC
Dai risultati della query, puoi notare che i viaggi in bicicletta da e verso la stazione Hyde Park Corner sono stati i più popolari.

Poi, fai doppio clic sulla tabella cycle_stations, che fornisce informazioni su ogni stazione.
Vogliamo unire le tabelle cycle_hire e cycle_stations. La tabella cycle_stations contiene la latitudine e la longitudine di ogni stazione. Utilizzerai queste informazioni per stimare la distanza percorsa in ogni viaggio in bicicletta calcolando la distanza tra le stazioni di partenza e di arrivo.
Per eseguire questo calcolo, utilizzerai le funzioni geografiche di BigQuery. Nello specifico, convertirai ogni stringa di latitudine/longitudine in un ST_GEOGPOINT e utilizzerai la funzione ST_DISTANCE per calcolare la distanza in linea retta in metri tra i due punti. Utilizzerai questo valore come proxy per la distanza percorsa in ogni viaggio in bicicletta.
Copia la seguente query nell'editor SQL e poi fai clic su Invia query. Tieni presente che nella condizione JOIN sono presenti tre tabelle perché dobbiamo unire la tabella delle stazioni due volte per ottenere la latitudine e la longitudine sia della stazione di partenza che di quella di arrivo della bicicletta.
WITH staging AS (
SELECT
STRUCT(
start_stn.name,
ST_GEOGPOINT(start_stn.longitude, start_stn.latitude) AS POINT,
start_stn.docks_count,
start_stn.install_date
) AS starting,
STRUCT(
end_stn.name,
ST_GEOGPOINT(end_stn.longitude, end_stn.latitude) AS point,
end_stn.docks_count,
end_stn.install_date
) AS ending,
STRUCT(
rental_id,
bike_id,
duration, --seconds
ST_DISTANCE(
ST_GEOGPOINT(start_stn.longitude, start_stn.latitude),
ST_GEOGPOINT(end_stn.longitude, end_stn.latitude)
) AS distance, --meters
start_date,
end_date
) AS bike
FROM `bigquery-public-data.london_bicycles.cycle_stations` AS start_stn
LEFT JOIN `bigquery-public-data.london_bicycles.cycle_hire` as b
ON start_stn.id = b.start_station_id
LEFT JOIN `bigquery-public-data.london_bicycles.cycle_stations` AS end_stn
ON end_stn.id = b.end_station_id
LIMIT 700000)
SELECT * from STAGING
6. Addestra un modello ML su un kernel TensorFlow
Vertex AI Workbench dispone di un livello di compatibilità di calcolo che consente di avviare kernel per TensorFlow, PySpark, R e così via, tutto da una singola istanza notebook. In questo lab, creerai un notebook utilizzando il kernel TensorFlow.
Crea DataFrame
Dopo l'esecuzione della query, fai clic su Copia codice per DataFrame. In questo modo potrai incollare il codice Python in un notebook che si connette al client BigQuery ed estrae questi dati come DataFrame Pandas.

A questo punto, torna al Launcher e crea un notebook TensorFlow 2.

Nella prima cella del blocco note, incolla il codice copiato dall'Editor query. Dovrebbe avere il seguente aspetto:
# The following two lines are only necessary to run once.
# Comment out otherwise for speed-up.
from google.cloud.bigquery import Client, QueryJobConfig
client = Client()
query = """WITH staging AS (
SELECT
STRUCT(
start_stn.name,
ST_GEOGPOINT(start_stn.longitude, start_stn.latitude) AS POINT,
start_stn.docks_count,
start_stn.install_date
) AS starting,
STRUCT(
end_stn.name,
ST_GEOGPOINT(end_stn.longitude, end_stn.latitude) AS point,
end_stn.docks_count,
end_stn.install_date
) AS ending,
STRUCT(
rental_id,
bike_id,
duration, --seconds
ST_DISTANCE(
ST_GEOGPOINT(start_stn.longitude, start_stn.latitude),
ST_GEOGPOINT(end_stn.longitude, end_stn.latitude)
) AS distance, --meters
start_date,
end_date
) AS bike
FROM `bigquery-public-data.london_bicycles.cycle_stations` AS start_stn
LEFT JOIN `bigquery-public-data.london_bicycles.cycle_hire` as b
ON start_stn.id = b.start_station_id
LEFT JOIN `bigquery-public-data.london_bicycles.cycle_stations` AS end_stn
ON end_stn.id = b.end_station_id
LIMIT 700000)
SELECT * from STAGING"""
job = client.query(query)
df = job.to_dataframe()
Ai fini di questo lab, limitiamo il set di dati a 700.000 per ridurre i tempi di addestramento. ma puoi modificare la query e sperimentare con l'intero set di dati.
Successivamente, importa le librerie necessarie.
from datetime import datetime
import pandas as pd
import tensorflow as tf
Esegui il seguente codice per creare un DataFrame ridotto che contenga solo le colonne necessarie per la parte di ML di questo esercizio.
values = df['bike'].values
duration = list(map(lambda a: a['duration'], values))
distance = list(map(lambda a: a['distance'], values))
dates = list(map(lambda a: a['start_date'], values))
data = pd.DataFrame(data={'duration': duration, 'distance': distance, 'start_date':dates})
data = data.dropna()
La colonna start_date è un datetime di Python. Anziché utilizzare questo datetime direttamente nel modello, creerai due nuove caratteristiche che indicano il giorno della settimana e l'ora del giorno in cui si è verificato il viaggio in bicicletta.
data['weekday'] = data['start_date'].apply(lambda a: a.weekday())
data['hour'] = data['start_date'].apply(lambda a: a.time().hour)
data = data.drop(columns=['start_date'])
Infine, converti la colonna della durata da secondi a minuti per facilitarne la comprensione
data['duration'] = data['duration'].apply(lambda x:float(x / 60))
Esamina le prime righe del DataFrame formattato. Per ogni corsa in bicicletta, ora hai a disposizione i dati sul giorno della settimana e l'ora del giorno in cui si è svolta la corsa, nonché la distanza percorsa. A partire da queste informazioni, proverai a prevedere la durata del viaggio.
data.head()

Prima di poter creare e addestrare il modello, devi dividere i dati in set di addestramento e validazione.
# Use 80/20 train/eval split
train_size = int(len(data) * .8)
print ("Train size: %d" % train_size)
print ("Evaluation size: %d" % (len(data) - train_size))
# Split data into train and test sets
train_data = data[:train_size]
val_data = data[train_size:]
Crea modello TensorFlow
Creerai un modello TensorFlow utilizzando l'API Keras Functional. Per pre-elaborare i dati di input, utilizzerai l'API degli strati di pre-elaborazione di Keras.
La seguente funzione di utilità creerà un tf.data.Dataset dal DataFrame Pandas.
def df_to_dataset(dataframe, label, shuffle=True, batch_size=32):
dataframe = dataframe.copy()
labels = dataframe.pop(label)
ds = tf.data.Dataset.from_tensor_slices((dict(dataframe), labels))
if shuffle:
ds = ds.shuffle(buffer_size=len(dataframe))
ds = ds.batch(batch_size)
ds = ds.prefetch(batch_size)
return ds
Utilizza la funzione precedente per creare due tf.data.Dataset, uno per l'addestramento e uno per la convalida. Potresti visualizzare alcuni avvisi, ma puoi ignorarli tranquillamente.
train_dataset = df_to_dataset(train_data, 'duration')
validation_dataset = df_to_dataset(val_data, 'duration')
Nel modello utilizzerai i seguenti livelli di pre-elaborazione:
- Layer di normalizzazione: esegue la normalizzazione delle caratteristiche di input in base alle caratteristiche.
- Strato IntegerLookup: trasforma i valori categorici interi in indici interi.
- Strato CategoryEncoding: trasforma le caratteristiche categoriche intere in rappresentazioni dense con codifica one-hot, multi-hot o TF-IDF.
Tieni presente che questi livelli non possono essere addestrati. Invece, imposti lo stato del livello di pre-elaborazione esponendolo ai dati di addestramento tramite il metodo adapt().
La seguente funzione creerà un livello di normalizzazione che puoi utilizzare nella funzionalità Distanza. Imposterai lo stato prima di adattare il modello utilizzando il metodo adapt() sui dati di addestramento. In questo modo verranno calcolati la media e la varianza da utilizzare per la normalizzazione. In seguito, quando trasmetti il set di dati di convalida al modello, vengono utilizzati la stessa media e la stessa varianza calcolate sui dati di addestramento per scalare i dati di convalida.
def get_normalization_layer(name, dataset):
# Create a Normalization layer for our feature.
normalizer = tf.keras.layers.Normalization(axis=None)
# Prepare a Dataset that only yields our feature.
feature_ds = dataset.map(lambda x, y: x[name])
# Learn the statistics of the data.
normalizer.adapt(feature_ds)
return normalizer
Allo stesso modo, la seguente funzione crea una codifica delle categorie che utilizzerai per le funzionalità ora e giorno della settimana.
def get_category_encoding_layer(name, dataset, dtype, max_tokens=None):
index = tf.keras.layers.IntegerLookup(max_tokens=max_tokens)
# Prepare a Dataset that only yields our feature
feature_ds = dataset.map(lambda x, y: x[name])
# Learn the set of possible values and assign them a fixed integer index.
index.adapt(feature_ds)
# Create a Discretization for our integer indices.
encoder = tf.keras.layers.CategoryEncoding(num_tokens=index.vocabulary_size())
# Apply one-hot encoding to our indices. The lambda function captures the
# layer so we can use them, or include them in the functional model later.
return lambda feature: encoder(index(feature))
Dopodiché, crea la parte di preelaborazione del modello. Innanzitutto, crea un livello tf.keras.Input per ciascuna delle funzionalità.
# Create a Keras input layer for each feature
numeric_col = tf.keras.Input(shape=(1,), name='distance')
hour_col = tf.keras.Input(shape=(1,), name='hour', dtype='int64')
weekday_col = tf.keras.Input(shape=(1,), name='weekday', dtype='int64')
Poi crea i livelli di normalizzazione e codifica delle categorie, memorizzandoli in un elenco.
all_inputs = []
encoded_features = []
# Pass 'distance' input to normalization layer
normalization_layer = get_normalization_layer('distance', train_dataset)
encoded_numeric_col = normalization_layer(numeric_col)
all_inputs.append(numeric_col)
encoded_features.append(encoded_numeric_col)
# Pass 'hour' input to category encoding layer
encoding_layer = get_category_encoding_layer('hour', train_dataset, dtype='int64')
encoded_hour_col = encoding_layer(hour_col)
all_inputs.append(hour_col)
encoded_features.append(encoded_hour_col)
# Pass 'weekday' input to category encoding layer
encoding_layer = get_category_encoding_layer('weekday', train_dataset, dtype='int64')
encoded_weekday_col = encoding_layer(weekday_col)
all_inputs.append(weekday_col)
encoded_features.append(encoded_weekday_col)
Dopo aver definito i livelli di preelaborazione, puoi definire il resto del modello. Concateni tutte le funzionalità di input e le passi a uno strato denso. Il livello di output è una singola unità, poiché si tratta di un problema di regressione.
all_features = tf.keras.layers.concatenate(encoded_features)
x = tf.keras.layers.Dense(64, activation="relu")(all_features)
output = tf.keras.layers.Dense(1)(x)
model = tf.keras.Model(all_inputs, output)
Infine, compila il modello.
model.compile(optimizer = tf.keras.optimizers.Adam(0.001),
loss='mean_squared_logarithmic_error')
Ora che hai definito il modello, puoi visualizzare l'architettura
tf.keras.utils.plot_model(model, show_shapes=True, rankdir="LR")

Tieni presente che questo modello è piuttosto complesso per questo semplice set di dati. È destinato a scopi dimostrativi.
Eseguiamo l'addestramento per un'epoca solo per verificare che il codice funzioni.
model.fit(train_dataset, validation_data = validation_dataset, epochs = 1)
Addestra il modello con una GPU
Dopodiché, addestrerai il modello più a lungo e utilizzerai lo strumento di cambio hardware per velocizzare l'addestramento. Vertex AI Workbench ti consente di modificare l'hardware senza arrestare l'istanza. Se aggiungi la GPU solo quando ti serve, puoi contenere i costi.
Per modificare il profilo hardware, fai clic sul tipo di macchina nell'angolo in alto a destra e seleziona Modifica hardware.

Seleziona Collega GPU e seleziona una GPU NVIDIA T4 Tensor Core.

La configurazione dell'hardware richiede circa cinque minuti. Una volta completato il processo, addestriamo il modello per un po' di tempo in più. Noterai che ogni epoca richiede meno tempo.
model.fit(train_dataset, validation_data = validation_dataset, epochs = 5)
🎉 Congratulazioni! 🎉
Hai imparato a utilizzare Vertex AI Workbench per:
- Esplora i dati in BigQuery
- Utilizzare il client BigQuery per caricare i dati in Python
- Addestra un modello TensorFlow con i livelli di pre-elaborazione di Keras e una GPU
Per saperne di più sulle diverse parti di Vertex AI, consulta la documentazione.
7. Esegui la pulizia
Poiché abbiamo configurato il notebook in modo che scada il timeout dopo 60 minuti di inattività, non dobbiamo preoccuparci di arrestare l'istanza. Se vuoi arrestare manualmente l'istanza, fai clic sul pulsante Arresta nella sezione Vertex AI Workbench della console. Se vuoi eliminare completamente il blocco note, fai clic sul pulsante Elimina.
