Tutorial: Erstellen, Auswerten und Bewerten eines Modells zur Erkennung von Maschinenfehlern

Dieses Tutorial stellt ein umfassendes Beispiel für einen Synapse Data Science-Workflow in Microsoft Fabric vor. Das Szenario verwendet maschinelles Lernen für einen systematischeren Ansatz für die Fehlerdiagnose, damit Probleme proaktiv identifiziert und Maßnahmen vor einem tatsächlichen Maschinenausfall ergriffen werden können. Das Ziel besteht darin, anhand von Prozesstemperatur, Drehzahl usw. vorherzusagen, ob bei einer Maschine ein Ausfall auftreten könnte.

Dieses Tutorial umfasst die folgenden Schritte:

  • Installieren von benutzerdefinierten Bibliotheken
  • Laden und Verarbeiten der Daten
  • Verstehen der Daten durch explorative Datenanalyse
  • Trainieren von Machine Learning-Modellen mit Scikit-Learn, LightGBM und MLflow und Nachverfolgen von Experimenten mit der automatischen Protokollierungsfunktion in Fabric
  • Bewerten der trainierten Modelle mithilfe der Fabric-PREDICT-Funktion, Speichern des besten Modells und Laden des Modells für Vorhersagen
  • Darstellen der Leistung des geladenen Modells mit Power BI-Visualisierungen

Voraussetzungen

Notebook für das Tutorial

Für das Notebook können Sie eine der folgenden Optionen wählen:

  • Öffnen Sie das integrierte Notebook in der Data Science-Umgebung, und führen Sie es aus
  • Laden Sie Ihr Notebook von GitHub in die Data Science-Umgebung hoch

Öffnen des integrierten Notebooks

Das Beispiel Maschinenausfall ist das Notebook, das dieses Tutorial begleitet.

So öffnen Sie das integrierte Beispiel-Notebook für das Tutorial in der Synapse Data Science-Umgebung:

  1. Wechseln Sie zur Synapse Data Science-Startseite.

  2. Wählen Sie Beispiel verwenden aus.

  3. Wählen Sie das zugehörige Beispiel aus:

    • Wählen Sie es auf der Standardregisterkarte End-to-End-Workflows (Python) aus, wenn es sich bei dem Beispiel um ein Python-Tutorial handelt.
    • Wählen Sie es auf der Registerkarte End-to-End-Workflows (R) aus, wenn es sich bei dem Beispiel um ein R-Tutorial handelt.
    • Wählen Sie es auf der Registerkarte Schnelltutorials aus, wenn es sich bei dem Beispiel um ein Schnelltutorial handelt.
  4. Fügen Sie ein Lakehouse an das Notebook an, bevor Sie mit der Ausführung von Code beginnen.

Importieren des Notebooks von GitHub

AISample – Predictive Maintenance ist das Notebook, das dieses Tutorial begleitet.

Befolgen Sie zum Öffnen des zugehörigen Notebooks für dieses Tutorial die Anweisungen unter Vorbereiten Ihres Systems für Data Science-Tutorials zum Importieren des Notebooks in Ihren Arbeitsbereich.

Wenn Sie den Code lieber von dieser Seite kopieren und einfügen möchten, können Sie auch ein neues Notebook erstellen.

Fügen Sie unbedingt ein Lakehouse an das Notebook an, bevor Sie mit der Ausführung von Code beginnen.

Schritt 1: Installieren von benutzerdefinierten Bibliotheken

Für die Entwicklung eines Machine Learning-Modells oder für Ad-hoc-Datenanalysen müssen Sie u. U. schnell eine benutzerdefinierte Bibliothek für Ihre Apache Spark-Sitzung installieren. Sie haben zwei Optionen zum Installieren von Bibliotheken.

  • Verwenden Sie die Inline-Installationsfunktionen (%pip oder %conda) Ihres Notebooks zum Erstellen einer Bibliothek nur in Ihrem aktuellen Notebook.
  • Alternativ können Sie eine Fabric-Umgebung erstellen, Bibliotheken aus öffentlichen Quellen installieren oder benutzerdefinierte Bibliotheken darauf hochladen, und dann kann Ihr Arbeitsbereichsadministrator die Umgebung als Standard für den Arbeitsbereich anfügen. Alle Bibliotheken in der Umgebung werden dann für die Verwendung in allen Notebooks und Spark-Auftragsdefinitionen im Arbeitsbereich verfügbar. Weitere Informationen zu Umgebungen finden Sie unter Erstellen, Konfigurieren und Verwenden einer Umgebung in Microsoft Fabric.

Verwenden Sie für dieses Tutorial %pip install zum Installieren der imblearn-Bibliothek in Ihrem Notebook.

Hinweis

Der PySpark-Kernel startet neu, nachdem %pip install gelaufen ist. Installieren Sie die benötigten Bibliotheken, bevor Sie andere Zellen ausführen.

# Use pip to install imblearn
%pip install imblearn

Schritt 2: Laden der Daten

Das Dataset simuliert die Protokollierung der Parameter einer Fertigungsmaschine als Zeitfunktion, was in industriellen Umgebungen üblich ist. Es besteht aus 10.000 Datenpunkten, die als Zeilen mit Funktionen als Spalten gespeichert werden. Zu den Funktionen gehören:

  • Ein eindeutiger Bezeichner (UID), der zwischen 1 und 10.000 liegt

  • Produkt-ID, bestehend aus einem Buchstaben L (für niedrig), M (für mittel) oder H (für hoch), der die Produktqualitätsvariante angibt, und einer variantenspezifischen Seriennummer. Niedrige, mittlere und hochwertige Varianten machen 60 %, 30 % bzw. 10 % aller Produkte aus

  • Lufttemperatur in Grad Kelvin (K)

  • Prozesstemperatur in Grad Kelvin

  • Drehzahl in Umdrehungen pro Minute (U/min)

  • Drehmoment in Newtonmeter (Nm)

  • Werkzeugverschleiß in Minuten. Bei den Qualitätsvarianten H, M und L kommen für das im Prozess verwendete Werkzeug 5, 3 bzw. 2 Minuten Werkzeugverschleiß hinzu

  • Eine Bezeichnung des Maschinenausfalls, die angibt, ob der Maschinenausfall am spezifischen Datenpunkt erfolgt ist. Dieser spezifische Datenpunkt kann einen der folgenden fünf unabhängigen Fehlerarten aufweisen:

    • Tool Wear Failure (TWF): Das Werkzeug wird bei einer zufällig ausgewählten Werkzeugverschleißzeit zwischen 200 und 240 Minuten ersetzt oder fällt aus
    • Heat Dissipation Failure (HDF): Die Wärmeableitung verursacht einen Prozessausfall, wenn die Differenz zwischen Lufttemperatur und Prozesstemperatur kleiner als 8,6 K und die Drehzahl des Werkzeugs kleiner als 1380 U/min ist
    • Power Failure (PWF): Das Ergebnis des Drehmoments und der Drehzahl (in Rad/s) entspricht der Leistung, die für den Prozess benötigt wird. Es kommt zu einem Prozessausfall, wenn diese Leistung unter 3500 W oder über 9000 W liegt
    • OverStrain Failure (OSF): Wenn das Produkt aus Werkzeugverschleiß und Drehmoment min. 11.000 Nm für die Produktvariante L (12.000 für M, 13.000 für H) überschreitet, kommt es zu einem Prozessausfall aufgrund einer Überlastung
    • Random Failures (RNF): Jeder Prozess hat unabhängig von den Prozessparametern eine Fehlerwahrscheinlichkeit von 0,1 %

Hinweis

Wenn mindestens einer der oben genannten Fehlermodi zutrifft, schlägt der Prozess fehl, und die Bezeichnung „Computerfehler“ ist auf „1“ festgelegt. Die Machine-Learning-Methode kann nicht ermitteln, welche Fehlerart den Prozessausfall verursacht hat.

Herunterladen des Datensatzes und Hochladen in Lakehouse

Stellen Sie eine Verbindung mit dem Azure Open Datasets-Container her, und laden Sie das Dataset „Predictive Maintenance“. Dieser Code lädt eine öffentlich verfügbare Version des Datasets herunter und speichert es dann in einem Fabric-Lakehouse:

Wichtig

Fügen Sie ein Lakehouse zum Notebook hinzu, bevor Sie es ausführen. Andernfalls wird eine Fehlermeldung angezeigt. Informationen zum Hinzufügen eines Lakehouse finden Sie unter Verbinden von Lakehouses und Notebooks.

# Download demo data files into the lakehouse if they don't exist
import os, requests
DATA_FOLDER = "Files/predictive_maintenance/"  # Folder that contains the dataset
DATA_FILE = "predictive_maintenance.csv"  # Data file name
remote_url = "https://synapseaisolutionsa.blob.core.windows.net/public/MachineFaultDetection"
file_list = ["predictive_maintenance.csv"]
download_path = f"/lakehouse/default/{DATA_FOLDER}/raw"

if not os.path.exists("/lakehouse/default"):
    raise FileNotFoundError(
        "Default lakehouse not found, please add a lakehouse and restart the session."
    )
os.makedirs(download_path, exist_ok=True)
for fname in file_list:
    if not os.path.exists(f"{download_path}/{fname}"):
        r = requests.get(f"{remote_url}/{fname}", timeout=30)
        with open(f"{download_path}/{fname}", "wb") as f:
            f.write(r.content)
print("Downloaded demo data files into lakehouse.")

Wenn Sie das Dataset in das Lakehouse heruntergeladen haben, können Sie es als Spark-DataFrame laden:

df = (
    spark.read.option("header", True)
    .option("inferSchema", True)
    .csv(f"{DATA_FOLDER}raw/{DATA_FILE}")
    .cache()
)
df.show(5)

Diese Tabelle enthält eine Vorschau der Daten:

UDI Product ID type Air temperature [K] Process temperature [K] Rotational speed [rpm] Torque [Nm] Tool wear [min] Ziel Fehlertyp
1 M14860 M 298.1 308.6 1551 42.8 0 0 Kein Fehler
2 L47181 L 298.2 308.7 1408 46,3 3 0 Kein Fehler
3 L47182 L 298.1 308,5 1498 49,4 5 0 Kein Fehler
4 L47183 L 298.2 308.6 1433 39,5 7 0 Kein Fehler
5 L47184 L 298.2 308.7 1408 40.0 9 0 Kein Fehler

Schreiben eines Spark-DataFrames in eine Lakehouse-Deltatabelle

Formatieren Sie die Daten (ersetzen Sie z. B. die Leerzeichen durch Unterstriche), um Spark-Vorgänge in den nachfolgenden Schritten zu erleichtern:

# Replace the space in the column name with an underscore to avoid an invalid character while saving 
df = df.toDF(*(c.replace(' ', '_') for c in df.columns))
table_name = "predictive_maintenance_data"
df.show(5)

Diese Tabelle enthält eine Vorschau der Daten mit neu formatierten Spaltennamen:

UDI Product_ID Typ Air_temperature_[K] Process_temperature_[K] Rotational_speed_[rpm] Torque_[Nm] Tool_wear_[min] Ziel Failure_Type
1 M14860 M 298.1 308.6 1551 42.8 0 0 Kein Fehler
2 L47181 L 298.2 308.7 1408 46,3 3 0 Kein Fehler
3 L47182 L 298.1 308,5 1498 49,4 5 0 Kein Fehler
4 L47183 L 298.2 308.6 1433 39,5 7 0 Kein Fehler
5 L47184 L 298.2 308.7 1408 40.0 9 0 Kein Fehler
# Save data with processed columns to the lakehouse 
df.write.mode("overwrite").format("delta").save(f"Tables/{table_name}")
print(f"Spark DataFrame saved to delta table: {table_name}")

Schritt 3: Vorverarbeitung von Daten und Durchführen einer explorativen Datenanalyse

Konvertieren Sie den Spark-DataFrame in einen Pandas-DataFrames, damit Sie die beliebten Pandas-kompatiblen Zeichnungsbibliotheken verwenden können.

Tipp

Bei einem großen Dataset müssen Sie möglicherweise einen Teil dieses Datasets laden.

data = spark.read.format("delta").load("Tables/predictive_maintenance_data")
SEED = 1234
df = data.toPandas()
df.drop(['UDI', 'Product_ID'],axis=1,inplace=True)
# Rename the Target column to IsFail
df = df.rename(columns = {'Target': "IsFail"})
df.info()

Konvertieren Sie bestimmte Spalten des Datasets nach Bedarf in Gleitkomma- oder Ganzzahltypen und ordnen Sie Zeichenketten ('L', 'M', 'H') numerischen Werten (0, 1. 2) zu:

# Convert temperature, rotational speed, torque, and tool wear columns to float
df['Air_temperature_[K]'] = df['Air_temperature_[K]'].astype(float)
df['Process_temperature_[K]'] = df['Process_temperature_[K]'].astype(float)
df['Rotational_speed_[rpm]'] = df['Rotational_speed_[rpm]'].astype(float)
df['Torque_[Nm]'] = df['Torque_[Nm]'].astype(float)
df['Tool_wear_[min]'] = df['Tool_wear_[min]'].astype(float)

# Convert the 'Target' column to an integer 
df['IsFail'] = df['IsFail'].astype(int)
# Map 'L', 'M', 'H' to numerical values 
df['Type'] = df['Type'].map({'L': 0, 'M': 1, 'H': 2})

Untersuchen von Daten mithilfe von Visualisierungen

# Import packages and set plotting style
import seaborn as sns
import matplotlib.pyplot as plt
import pandas as pd
sns.set_style('darkgrid')

# Create the correlation matrix
corr_matrix = df.corr(numeric_only=True)

# Plot a heatmap
plt.figure(figsize=(10, 8))
sns.heatmap(corr_matrix, annot=True)
plt.show()

Screenshot showing a plot of the correlation matrix of features.

Wie erwartet, korreliert der Ausfall (IsFail) mit den ausgewählten Features (Spalten). Die Korrelationsmatrix zeigt, dass Air_temperature, Process_temperature, Rotational_speed, Torque und Tool_wear die höchste Korrelation mit der IsFail-Variablen aufweisen.

# Plot histograms of select features
fig, axes = plt.subplots(2, 3, figsize=(18,10))
columns = ['Air_temperature_[K]', 'Process_temperature_[K]', 'Rotational_speed_[rpm]', 'Torque_[Nm]', 'Tool_wear_[min]']
data=df.copy()
for ind, item in enumerate (columns):
    column = columns[ind]
    df_column = data[column]
    df_column.hist(ax = axes[ind%2][ind//2], bins=32).set_title(item)
fig.supylabel('count')
fig.subplots_adjust(hspace=0.2)
fig.delaxes(axes[1,2])

Screenshot showing a graph plot of the features.

Wie aus den Diagrammen ersichtlich ist, sind die Variablen Air_temperature, Process_temperature, Rotational_speed, Torque und Tool_wear nicht spärlich. Sie scheinen eine gute Kontinuität im Featurebereich zu haben. Diese Plots bestätigen, dass das Trainieren eines Machine Learning-Modells für dieses Dataset voraussichtlich zuverlässige Ergebnisse liefert, die zu einem neuen Dataset generalisiert werden können.

Überprüfen der Zielvariablen auf Klassenungleichheit

Zählen Sie die Anzahl der Beispiele für ausgefallene und nicht ausgefallene Maschinen, und überprüfen Sie die Ausgeglichenheit der Daten für jede Klasse (IsFail=0, IsFail=1):

# Plot the counts for no failure and each failure type
plt.figure(figsize=(12, 2))
ax = sns.countplot(x='Failure_Type', data=df)
for p in ax.patches:
    ax.annotate(f'{p.get_height()}', (p.get_x()+0.4, p.get_height()+50))

plt.show()

# Plot the counts for no failure versus the sum of all failure types
plt.figure(figsize=(4, 2))
ax = sns.countplot(x='IsFail', data=df)
for p in ax.patches:
    ax.annotate(f'{p.get_height()}', (p.get_x()+0.4, p.get_height()+50))

plt.show()

Screenshot of a plot showing that samples are imbalanced.

Die Plots geben an, dass die Klasse ohne Ausfall (IsFail=0 im zweiten Plot) den Großteil der Stichproben darstellt. Verwenden Sie eine Oversampling-Methode, um ein ausgeglicheneres Trainingsdataset zu erstellen:

# Separate features and target
features = df[['Type', 'Air_temperature_[K]', 'Process_temperature_[K]', 'Rotational_speed_[rpm]', 'Torque_[Nm]', 'Tool_wear_[min]']]
labels = df['IsFail']

# Split the dataset into the training and testing sets
from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split(features, labels, test_size=0.2, random_state=42)

# Ignore warnings
import warnings
warnings.filterwarnings('ignore')
# Save test data to the lakehouse for use in future sections
table_name = "predictive_maintenance_test_data"
df_test_X = spark.createDataFrame(X_test)
df_test_X.write.mode("overwrite").format("delta").save(f"Tables/{table_name}")
print(f"Spark DataFrame saved to delta table: {table_name}")

Oversamplen zum Ausgleich der Klassen im Trainingsdataset

Die vorherige Analyse hat gezeigt, dass das Dataset stark unausgeglichen ist. Diese Unausgeglichenheit stellt ein Problem dar, weil es zu wenige Beispiele für die Minderheitsklasse für ein Modell gibt, um die Entscheidungsgrenze effektiv zu erlernen.

SMOTE kann das Problem lösen. SMOTE ist eine weit verbreitete Oversampling-Methode, die synthetische Beispiele generiert. Sie generiert Beispiele für die Minderheitsklasse basierend auf dem euklidischen Abstand zwischen Datenpunkten. Diese Methode unterscheidet sich vom zufälligen Oversampling, da sie neue Beispiele erstellt, die nicht nur die Minderheitsklasse duplizieren. Die Methode wird zu einer effektiveren Technik zur Behandlung von unausgeglichenen Datasets.

# Disable MLflow autologging because you don't want to track SMOTE fitting
import mlflow

mlflow.autolog(disable=True)

from imblearn.combine import SMOTETomek
smt = SMOTETomek(random_state=SEED)
X_train_res, y_train_res = smt.fit_resample(X_train, y_train)

# Plot the counts for both classes
plt.figure(figsize=(4, 2))
ax = sns.countplot(x='IsFail', data=pd.DataFrame({'IsFail': y_train_res.values}))
for p in ax.patches:
    ax.annotate(f'{p.get_height()}', (p.get_x()+0.4, p.get_height()+50))

plt.show()

Screenshot of a plot showing that samples are balanced.

Sie haben das Dataset erfolgreich ausgeglichen. Sie können jetzt zum Modelltraining übergehen.

Schritt 4: Trainieren und Auswerten der Modelle

MLflow registriert Modelle, trainiert und vergleicht verschiedene Modelle und wählt das beste Modell für Vorhersagezwecke. Für das Modelltraining können Sie die folgenden drei Modelle verwenden:

  • Zufälliger Gesamtstrukturklassifizierung
  • Logistische Regressionsklassifizierung
  • XGBoost-Klassifizierung

Trainieren einer zufälligen Gesamtstrukturklassifizierung

import numpy as np 
from sklearn.ensemble import RandomForestClassifier
from mlflow.models.signature import infer_signature
from sklearn.metrics import f1_score, accuracy_score, recall_score

mlflow.set_experiment("Machine_Failure_Classification")
mlflow.autolog(exclusive=False) # This is needed to override the preconfigured autologging behavior

with mlflow.start_run() as run:
    rfc_id = run.info.run_id
    print(f"run_id {rfc_id}, status: {run.info.status}")
    rfc = RandomForestClassifier(max_depth=5, n_estimators=50)
    rfc.fit(X_train_res, y_train_res) 
    signature = infer_signature(X_train_res, y_train_res)

    mlflow.sklearn.log_model(
        rfc,
        "machine_failure_model_rf",
        signature=signature,
        registered_model_name="machine_failure_model_rf"
    ) 

    y_pred_train = rfc.predict(X_train)
    # Calculate the classification metrics for test data
    f1_train = f1_score(y_train, y_pred_train, average='weighted')
    accuracy_train = accuracy_score(y_train, y_pred_train)
    recall_train = recall_score(y_train, y_pred_train, average='weighted')

    # Log the classification metrics to MLflow
    mlflow.log_metric("f1_score_train", f1_train)
    mlflow.log_metric("accuracy_train", accuracy_train)
    mlflow.log_metric("recall_train", recall_train)

    # Print the run ID and the classification metrics
    print("F1 score_train:", f1_train)
    print("Accuracy_train:", accuracy_train)
    print("Recall_train:", recall_train)    

    y_pred_test = rfc.predict(X_test)
    # Calculate the classification metrics for test data
    f1_test = f1_score(y_test, y_pred_test, average='weighted')
    accuracy_test = accuracy_score(y_test, y_pred_test)
    recall_test = recall_score(y_test, y_pred_test, average='weighted')

    # Log the classification metrics to MLflow
    mlflow.log_metric("f1_score_test", f1_test)
    mlflow.log_metric("accuracy_test", accuracy_test)
    mlflow.log_metric("recall_test", recall_test)

    # Print the classification metrics
    print("F1 score_test:", f1_test)
    print("Accuracy_test:", accuracy_test)
    print("Recall_test:", recall_test)

Aus der Ausgabe geht hervor, dass sowohl das Trainings- als auch das Testdataset mit der zufälligen Gesamtstrukturklassifizierung einen F1-Score, eine Genauigkeit und eine Wiedererkennung von ungefähr 0,9 erzielen.

Trainieren einer logistischen Regressionsklassifizierung

from sklearn.linear_model import LogisticRegression

with mlflow.start_run() as run:
    lr_id = run.info.run_id
    print(f"run_id {lr_id}, status: {run.info.status}")
    lr = LogisticRegression(random_state=42)
    lr.fit(X_train_res, y_train_res)
    signature = infer_signature(X_train_res, y_train_res)
  
    mlflow.sklearn.log_model(
        lr,
        "machine_failure_model_lr",
        signature=signature,
        registered_model_name="machine_failure_model_lr"
    ) 

    y_pred_train = lr.predict(X_train)
    # Calculate the classification metrics for training data
    f1_train = f1_score(y_train, y_pred_train, average='weighted')
    accuracy_train = accuracy_score(y_train, y_pred_train)
    recall_train = recall_score(y_train, y_pred_train, average='weighted')

    # Log the classification metrics to MLflow
    mlflow.log_metric("f1_score_train", f1_train)
    mlflow.log_metric("accuracy_train", accuracy_train)
    mlflow.log_metric("recall_train", recall_train)

    # Print the run ID and the classification metrics
    print("F1 score_train:", f1_train)
    print("Accuracy_train:", accuracy_train)
    print("Recall_train:", recall_train)    

    y_pred_test = lr.predict(X_test)
    # Calculate the classification metrics for test data
    f1_test = f1_score(y_test, y_pred_test, average='weighted')
    accuracy_test = accuracy_score(y_test, y_pred_test)
    recall_test = recall_score(y_test, y_pred_test, average='weighted')

    # Log the classification metrics to MLflow
    mlflow.log_metric("f1_score_test", f1_test)
    mlflow.log_metric("accuracy_test", accuracy_test)
    mlflow.log_metric("recall_test", recall_test)

Trainieren einer XGBoost-Klassifizierung

from xgboost import XGBClassifier

with mlflow.start_run() as run:
    xgb = XGBClassifier()
    xgb_id = run.info.run_id 
    print(f"run_id {xgb_id}, status: {run.info.status}")
    xgb.fit(X_train_res.to_numpy(), y_train_res.to_numpy()) 
    signature = infer_signature(X_train_res, y_train_res)
  
    mlflow.xgboost.log_model(
        xgb,
        "machine_failure_model_xgb",
        signature=signature,
        registered_model_name="machine_failure_model_xgb"
    ) 

    y_pred_train = xgb.predict(X_train)
    # Calculate the classification metrics for training data
    f1_train = f1_score(y_train, y_pred_train, average='weighted')
    accuracy_train = accuracy_score(y_train, y_pred_train)
    recall_train = recall_score(y_train, y_pred_train, average='weighted')

    # Log the classification metrics to MLflow
    mlflow.log_metric("f1_score_train", f1_train)
    mlflow.log_metric("accuracy_train", accuracy_train)
    mlflow.log_metric("recall_train", recall_train)

    # Print the run ID and the classification metrics
    print("F1 score_train:", f1_train)
    print("Accuracy_train:", accuracy_train)
    print("Recall_train:", recall_train)    

    y_pred_test = xgb.predict(X_test)
    # Calculate the classification metrics for test data
    f1_test = f1_score(y_test, y_pred_test, average='weighted')
    accuracy_test = accuracy_score(y_test, y_pred_test)
    recall_test = recall_score(y_test, y_pred_test, average='weighted')

    # Log the classification metrics to MLflow
    mlflow.log_metric("f1_score_test", f1_test)
    mlflow.log_metric("accuracy_test", accuracy_test)
    mlflow.log_metric("recall_test", recall_test)

Schritt 5: Auswählen des besten Modells und Vorhersagen von Ausgaben

Im vorherigen Abschnitt haben Sie drei verschiedene Klassifizierungen trainiert: Zufällige Gesamtstruktur, Logistische Regression und XGBoost. Sie haben nun die Wahl, entweder programmgesteuert auf die Ergebnisse zuzugreifen oder die Benutzeroberfläche (UI) zu verwenden.

Navigieren Sie für den Weg über die Benutzeroberfläche zu Ihrem Arbeitsbereich und filtern Sie die Modelle.

Screenshot of the filter, with models selected.

Wählen Sie einzelne Modelle aus, um Details zur Modellleistung anzuzeigen.

Screenshot of performance details for models.

Dieses Beispiel zeigt, wie Sie programmgesteuert über MLflow auf die Modelle zugreifen:

runs = {'random forest classifier':   rfc_id,
        'logistic regression classifier': lr_id,
        'xgboost classifier': xgb_id}

# Create an empty DataFrame to hold the metrics
df_metrics = pd.DataFrame()

# Loop through the run IDs and retrieve the metrics for each run
for run_name, run_id in runs.items():
    metrics = mlflow.get_run(run_id).data.metrics
    metrics["run_name"] = run_name
    df_metrics = df_metrics.append(metrics, ignore_index=True)

# Print the DataFrame
print(df_metrics)

XGBoost erzielt zwar die besten Ergebnisse mit dem Trainingssatz, schneidet aber beim Testdataset schlecht ab. Diese schlechte Leistung deutet auf eine Überanpassung hin. Die logistische Regressionsklassifizierung schneidet sowohl bei Trainings- als auch bei Testdatasets schlecht ab. Insgesamt stellt die zufällige Gesamtstrukturklassifizierung eine gute Balance zwischen Trainingsleistung und Vermeidung von Überanpassung dar.

Wählen Sie im nächsten Abschnitt das registrierte Gesamtstrukturmodell aus, und führen Sie eine Vorhersage mithilfe der PREDICT-Funktion durch:

from synapse.ml.predict import MLFlowTransformer

model = MLFlowTransformer(
    inputCols=list(X_test.columns),
    outputCol='predictions',
    modelName='machine_failure_model_rf',
    modelVersion=1
)

Mit dem erstellten MLFlowTransformer-Objekt zum Laden des Modells für Rückschlüsse können Sie über die Transformer-API das Modell für das Testdataset bewerten:

predictions = model.transform(spark.createDataFrame(X_test))
predictions.show()

Diese Tabelle enthält die Ausgabe:

Typ Air_temperature_[K] Process_temperature_[K] Rotational_speed_[rpm] Torque_[Nm] Tool_wear_[min] vorhersagen
0 300,6 309,7 1639.0 30,4 121,0 0
0 303,9 313,0 1551,0 36,8 140,0 0
1 299,1 308.6 1491,0 38.5 166,0 0
0 300,9 312,1 1359,0 51,7 146,0 1
0 303,7 312,6 1621,0 38.8 182,0 0
0 299,0 310,3 1868,0 24.0 221,0 1
2 297,8 307,5 1631.0 31.3 124,0 0
0 297,5 308,2 1327,0 56,5 189,0 1
0 301,3 310,3 1460,0 41,5 197,0 0
2 297,6 309,0 1413,0 40.2 51.0 0
1 300,9 309,4 1724,0 25.6 119,0 0
0 303,3 311,3 1389,0 53,9 39,0 0
0 298,4 307,9 1981,0 23,2 16,0 0
0 299,3 308,8 1636,0 29.9 201,0 0
1 298.1 309,2 1460,0 45,8 80.0 0
0 300,0 309,5 1728,0 26,0 37.0 0
2 299,0 308.7 1940,0 19,9 98,0 0
0 302,2 310,8 1383,0 46,9 45,0 0
0 300,2 309,2 1431,0 51,3 57.0 0
0 299,6 310,2 1468.0 48.0 9.0 0

Speichern von Daten im Lakehouse. Die Daten stehen dann für den späteren Gebrauch zur Verfügung – z. B. für ein Power BI-Dashboard.

# Save test data to the lakehouse for use in the next section. 
table_name = "predictive_maintenance_test_with_predictions"
predictions.write.mode("overwrite").format("delta").save(f"Tables/{table_name}")
print(f"Spark DataFrame saved to delta table: {table_name}")

Schritt 6: Anzeigen von Business Intelligence über Visualisierungen in Power BI

Zeigen Sie die Ergebnisse mit einem Power BI-Dashboard in einem Offlineformat an.

Screenshot of the data displayed as a Power BI dashboard.

Die Dashboard zeigt, dass Tool_wear und Torque eine spürbare Grenze zwischen Fällen mit und ohne Ausfall bilden, wie nach der früheren Korrelationsanalyse in Schritt 2 zu erwarten.