Distribuire il modello di analisi dei dati nell'app di Windows con le API di Windows ML
Nella parte precedente di questa esercitazione si è appreso come compilare ed esportare un modello in formato ONNX. Verrà ora illustrato come incorporare il modello esportato in un'applicazione Windows ed eseguirlo in locale in un dispositivo chiamando le API di Windows ML.
Al termine, si avrà un'app di analisi dei dati funzionante.
Informazioni sull'app di esempio
In questo passaggio dell'esercitazione si creerà un'app in grado di analizzare i dati tabulari di Iris. L'app consente di aggiungere il file excel con le informazioni di input necessarie o immettere manualmente i parametri di input, ovvero la lunghezza e la larghezza del sepale e del petalo iris in cm. Queste funzionalità verranno elaborate da un modello ONNX della rete neurale archiviata in locale creato e sottoposto a training nella parte precedente. In base all'output del modello, l'app visualizzerà il tipo Iris corretto.
In questo caso, verrà illustrato questo processo.
Nota
Se si sceglie di usare l'esempio di codice predefinito, è possibile clonare il file della soluzione. Clonare il repository, passare a questo esempio e aprire il Iris Data Analysis.csproj
file con Visual Studio.Skip alla parte Avvia applicazione di questa pagina per visualizzarla in uso.
Di seguito verrà illustrato come creare l'app e aggiungere codice windows ML.
Creare un'app Desktop di Windows ML (C#)
Per creare un'app di Windows ML funzionante, è necessario eseguire le operazioni seguenti:
- Caricare un modello di Machine Learning.
- Associare gli input e gli output del modello.
- Valutare il modello e visualizzare risultati significativi.
Dovrai anche creare un'interfaccia utente di base per offrire un'esperienza utente migliore.
Aprire un nuovo progetto in Visual Studio
- Iniziamo. Aprire Visual Studio e scegliere
Create a new project
.
- Nella barra di ricerca scegliere
C#
come lingua,Windows
come piattaforma di destinazione eDektop
come tipo di progetto. SelezionareNUnit Test Project (.NET Core)
come tipo di progetto e selezionarenext
per aprire una finestra di configurazione per il progetto.
- Nella finestra di configurazione eseguire le operazioni seguenti:
- Assegnare un nome al progetto. In questo caso, viene chiamato Iris Data Analysis.
- Scegliere il percorso del progetto.
- Se si usa VS2019, verificare che
Create directory for solution
sia selezionata. - Se si usa VS2017, verificare che
Place solution and project in the same directory
sia deselezionata.
Premere create
per creare il progetto. È possibile che venga visualizzata la finestra della versione di destinazione minima. Assicurarsi che la versione minima sia impostata su Windows 10, versione 1809 (10.0; build 17763) o successiva.
- Dopo aver creato il progetto, passare alla cartella del progetto, aprire la cartella
[….\DataClassifier\Assets]
assets e copiare ilNetwork.onnx
file in questo percorso.
Esplorare la soluzione del progetto
Si esaminerà ora la soluzione del progetto.
Visual Studio ha creato automaticamente diversi file cs-code all'interno del Esplora soluzioni. MainPage.xaml
contiene il codice XAML per l'interfaccia utente grafica e MainPage.xaml.cs
contiene il codice dell'applicazione. Se hai creato un'app UWP in precedenza, questi file dovrebbero essere molto familiari.
Anche se il file è stato aggiunto Network.onnx
alla cartella assets, è necessario aggiungerlo correttamente a questo progetto.
- Fare clic con il pulsante destro del mouse sulla cartella Assets nel Esplora soluzioni e scegliere
Add > Existing Item
. - Passare alla cartella Assets all'interno
Iris Data Analysis [….\Iris Data Analysis \Assets]
di , individuare l'elementoNetwork.onnx model
copiato in precedenza e selezionareAdd
. - Per assicurarsi che il modello venga compilato durante la compilazione dell'applicazione, fare clic con il pulsante destro del
Network.onnx
mouse sul file e selezionareProperties
. ImpostaBuild Action
suContent
.
È anche necessario creare un nuovo file di classe cs-code per contenere codice aggiuntivo di Machine Learning, che include classi e metodi che chiameranno le API di Windows ML.
- Fare clic con il pulsante destro del mouse sul nome della soluzione in Visual Studio e scegliere
add
enew item
. Nella finestra aperta selezionareClass
e assegnare un nome. In questo caso si usaIrisModel.cs
. Un nuovo file di classe farà appello nel progetto.
.
Creare codice di Machine Learning
In questo passaggio verranno creati tutti i metodi e le classi che chiameranno le API di Windows Machine Learning. Questi consentono di caricare, associare e valutare un modello di Machine Learning ONNX nel progetto.
Fare doppio clic sul
IrisModel.cs
file.Sostituire le istruzioni using con le istruzioni seguenti per ottenere l'accesso a tutte le API necessarie.
using System;
using System.Linq;
using System.Threading.Tasks;
using Windows.AI.MachineLearning;
using Windows.Storage;
Inizializzare le classi di Machine Learning
È necessario aggiungere diverse classi per IrisModel.cs
consentire l'interazione con le API di Windows Machine Learning.
Per ottenere l'accesso al modello di Machine Learning sottoposto a training, si userà la LearningModel
classe . Questa classe fa parte dello spazio dei Windows.AI.MachineLearning
nomi e rappresenta un modello di Machine Learning sottoposto a training. Una volta creata un'istanza, è l'oggetto LearningModel
principale usato per interagire con le API di Windows ML.
Per valutare il modello di apprendimento, è necessario creare una sessione di valutazione. A tale scopo, usare la LearningModelSession
classe . Questa classe viene usata per valutare i modelli di Machine Learning e associa il modello a un dispositivo che esegue e valuta il modello. Quando si crea una sessione con questa API, è anche possibile selezionare un dispositivo per eseguire il modello (il valore predefinito è la CPU).
È anche necessario specificare le etichette dell'output dei modelli di Machine Learning. È possibile connettere tali etichette all'output previsto del modello in un secondo momento.
Nota
Per altre informazioni su LearningModel
e LearningModelSession
classi, vedere la documentazione della classe LearningModel e la documentazione della classe LearningModelSession.
- Copiare il codice seguente nel
IrisModel.cs
file .
class IrisModel
{
private LearningModel _learning_model;
private LearningModelSession _session;
private String[] _labels = { "Iris-setosa", "Iris-versicolor", "Iris-virginica"};
Caricare il modello
Sarà quindi necessario caricare il modello di Machine Learning e creare una sessione, che verrà eseguita con le classi appena definite. Per caricare il modello, si useranno diversi metodi statici della LearningModel
classe, in questo caso si userà LoadFrom Archiviazione FileAsync, che consente di caricare un modello ONNX da un'istanza ISorageFile
asincrona.
Nota
Per altre informazioni sui modi aggiuntivi per caricare il modello, vedere la documentazione caricare un modello.
- Copiare il codice seguente nel
IrisModel.cs
file .
public async Task Initialize()
{
// Load and create the model and session
var modelFile = await StorageFile.GetFileFromApplicationUriAsync(new Uri($"ms-appx:///Assets//Network.onnx"));
_learning_model = await LearningModel.LoadFromStorageFileAsync(modelFile);
_session = new LearningModelSession(_learning_model);
}
Definire il tensore di input del modello
A questo punto, verrà definito l'input corretto in base ai requisiti del modello. Il modello di rete compilato nella parte precedente ha quattro valori di input. Ogni valore di input rappresenta le dimensioni possibili di quattro caratteristiche di iris: lunghezza sepale in cm, larghezza del sepale in cm, lunghezza dei petali in cm e larghezza petalo in cm. In base a questo input, il modello restituirà il tipo iris più adatto a tali parametri. Per questa esercitazione è necessario limitare le dimensioni dei valori di input ai valori logici validi. Per questa esercitazione si userà quanto segue:
- lunghezza sepal - da 1cm a 100cm
- larghezza sepal : da 1 cm a 8 cm
- lunghezza petalo - da 0,5 cm a 10 cm
- larghezza dei petali : da 0,1 cm a 5 cm
- Copiare il codice seguente nel
IrisModel.cs
file .
private float _sepal_length = 1.0f;
public float Sepal_Length
{
get
{
return _sepal_length;
}
set
{
// validate range [1,10]
if (value >= 1 && value <= 10)
{
_sepal_length = value;
}
}
}
private float _sepal_width = 1.0f;
public float Sepal_Width
{
get
{
return _sepal_width;
}
set
{
// validate range [1, 8]
if (value >= 1 && value <= 8)
{
_sepal_width = value;
}
}
}
private float _petal_length = 0.5f;
public float Petal_Length
{
get
{
return _petal_length;
}
set
{
// validate range [0.5, 10]
if (value >= 0.5 && value <= 10)
{
_petal_length = value;
}
}
}
private float _petal_width = 0.1f;
public float Petal_Width
{
get
{
return _petal_width;
}
set
{
// validate range [0.1, 5]
if (value >= 0.1 && value <= 5)
{
_petal_width = value;
}
}
}
Le API di Windows ML accettano valori di input delle quattro classi descrittive supportate dai modelli ONNX: tensori, sequenze, mappe e immagini. In questo caso, il modello richiede un oggetto float a 32 bit in una forma float32[batch_size,4]. Poiché la dimensione del batch è 1, la forma del tensore di input è [1x4].
Per creare un input tensor, si userà la classe TensorFloat .
La TensorFloat
classe fa parte dello spazio dei Windows.AI.MachineLearning
nomi e viene usata per definire un oggetto tensore float a 32 bit, ovvero un tensore di valori a virgola mobile a 32 bit. Questa classe contiene diversi metodi utili per compilare un tensore. In questo caso, si userà il metodo CreateFromArray per compilare un input tensor nella dimensione esatta richiesta dal modello. Questa chiamata verrà aggiunta all'interno del metodo di valutazione.
Associare e valutare il modello
Dopo aver definito il tensore di input del modello e aver creato un'istanza del modello e della sessione con training, è possibile creare un metodo per associare e valutare il modello di Machine Learning sottoposto a training.
Questo metodo è la parte fondamentale di un'app di Machine Learning. Include la tensorizzazione dei valori di input e l'associazione dell'input del modello. Questo modello verrà usato più avanti nel codice dell'applicazione per valutare il modello.
Per associare input e output, usare la LearningModelBinding
classe . Un modello di Machine Learning include caratteristiche di input e output, che passano informazioni all'interno e all'esterno del modello. Tenere presente che le funzionalità necessarie devono essere supportate dalle API di Windows ML. La LearningModelBinding
classe viene applicata a un LearningModelSession
oggetto per associare valori alle funzionalità di input e output denominate.
La LearningModelBinding
classe include diversi metodi predefiniti che è possibile usare per associare valori a tali funzionalità denominate. In questo caso si userà il Bind
metodo per associare i valori al modello.
Per valutare il modello e ricevere i risultati da esso, chiamare i metodi di evauazione predefiniti di ripetizione da LearningModelSession
, nel caso specifico, il Evaluate
metodo . Questo metodo fornirà la funzionalità necessaria, valutando il modello di Machine Learning usando i valori delle funzionalità forniti dalla LearningModelBinding
classe .
Nota
Per informazioni su altri metodi di valutazione per eseguire il modello, verificare quali metodi possono essere implementati in LearningModelSession esaminando la documentazione della classe LearningModelSession.
Estrarre e visualizzare i risultati
Il modello restituisce i valori stimati in formato tensor come output float tensor. Sarà ora necessario estrarre l'output del modello e visualizzare i risultati corretti. A tale scopo, si convertirà il formato del tensore in un vettore eseguendo la GetAsVectorView()
funzione nell'output predicato.
Il modello restituisce tre valori di probabilità, ognuno dei quali rappresenta un tipo iris specifico. Sarà necessario restituire l'etichetta con la probabilità più alta.
- Copiare il codice seguente nel
IrisModel.cs
file .
internal String Evaluate()
{
// input tensor shape is [1x4]
long[] shape = new long[2];
shape[0] = 1;
shape[1] = 4;
// set up the input tensor
float[] input_data = new float[4];
input_data[0] = _sepal_length;
input_data[1] = _sepal_width;
input_data[2] = _petal_length;
input_data[3] = _petal_width;
TensorFloat tensor_float = TensorFloat.CreateFromArray(shape, input_data);
// bind the tensor to "input"
var binding = new LearningModelBinding(_session);
binding.Bind("input", tensor_float);
// evaluate
var results = _session.Evaluate(binding, "");
// get the results
TensorFloat prediction = (TensorFloat)results.Outputs.First().Value;
var prediction_data = prediction.GetAsVectorView();
// find the highest predicted value
int max_index = 0;
float max_value = 0;
for (int i = 0; i < prediction_data.Count; i++)
{
var val = prediction_data.ElementAt(i);
if (val > max_value)
{
max_value = val;
max_index = i;
}
}
// return the label corresponding to the highest predicted value
return _labels.ElementAt(max_index);
}
A questo punto è stata completata la parte di Machine Learning del codice. A questo punto, è possibile integrare facilmente il modello con l'applicazione Windows. Nell'ultima parte di questa esercitazione è stata fornita un'interfaccia utente grafica e codice di controllo di Windows di base per testare il modello, usando i metodi già creati.
Creare l'interfaccia utente grafica dell'applicazione
Per creare un codice dell'app GUI per l'app, fare doppio clic sul file di
MainPage.xaml
codice e aprire un modello predefinito per l'interfaccia utente grafica.Copiare il codice seguente in
MainPage.xaml
, sotto la“Background="{ThemeResource ApplicationPageBackgroundThemeBrush}" " Height="939">
riga .
<Grid Margin="30,30,30,30">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock x:Name="title" HorizontalAlignment="Left" Text="Data Analysis App - Windows ML" TextWrapping="Wrap" VerticalAlignment="Top" FontSize="32" TextDecorations="Underline" FontWeight="Bold"/>
<TextBlock x:Name="subtitle" HorizontalAlignment="Left" Text="Provide the input :" TextWrapping="Wrap" VerticalAlignment="Top" FontSize="20" Grid.Row="1" FontWeight="Bold"/>
<Grid Grid.Row="2">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<TextBlock x:Name="sepal_length" Text="sepal length in mm [range of 10 - 100]:" VerticalAlignment="Center"/>
<TextBlock x:Name="sepal_width" Text="sepal width in mm [range of 10 - 80]:" VerticalAlignment="Center" Grid.Row="1"/>
<TextBlock x:Name="petal_length" Text="petal length in mm [range of 5 - 100]:" VerticalAlignment="Center" Grid.Row="2"/>
<TextBlock x:Name="petal_width" Text="sepal width in mm [range of 1 - 50]:" VerticalAlignment="Center" Grid.Row="3"/>
<Slider x:Name="sepal_length_input" Minimum="10" Maximum="100" Orientation="Horizontal" Grid.Column="1" Width="200" ValueChanged="sepal_length_input_ValueChanged"/>
<Slider x:Name="sepal_width_input" Minimum="10" Maximum="80" Orientation="Horizontal" Grid.Row="1" Grid.Column="1" Width="200" ValueChanged="sepal_width_input_ValueChanged"/>
<Slider x:Name="petal_length_input" Minimum="5" Maximum="100" Orientation="Horizontal" Grid.Row="2" Grid.Column="1" Width="200" ValueChanged="petal_length_input_ValueChanged"/>
<Slider x:Name="petal_width_input" Minimum="1" Maximum="50" Orientation="Horizontal" Grid.Row="3" Grid.Column="1" Width="200" ValueChanged="petal_width_input_ValueChanged"/>
</Grid>
<TextBlock x:Name="output" Text="Output:" FontSize="20" FontWeight="Bold" Grid.Row="3"/>
<Grid Grid.Row="4">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<TextBlock x:Name="output_subtitle" Text="Based on the information provided, the Iris type is:"/>
<TextBlock x:Name="model_output" Text="Model output" FontStyle="Italic" Grid.Column="1" Margin="10,0,0,0"/>
</Grid>
</Grid>
Creare il controllo dell'applicazione
Il codice di controllo dell'applicazione, MainPage.xaml.cs
, include il metodo principale per eseguire l'app e diversi passaggi per eseguire il modello ed eseguire l'output:
- Verrà creata un'istanza di un nuovo oggetto della
IrisModel
classe creata in precedenza in questa esercitazione. - Si chiamerà il
Evaluate()
metodo compilato nella parte precedente del modello. Questo metodo verrà applicato quattro volte, uno per ognuno dei parametri di input: lunghezza sepale, larghezza del sepale, lunghezza petalo e larghezza petalo.
L'app visualizzerà il risultato in base all'algoritmo di stima di Machine Learning.
- Per creare un codice di controllo dell'applicazione, fare doppio clic sul
MainPage.xaml.cs
file di codice e aggiungere il codice seguente.
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Controls.Primitives;
// The Blank Page item template is documented at https://go.microsoft.com/fwlink/?LinkId=402352&clcid=0x409
namespace Iris_Data_Analysis
{
/// <summary>
/// An empty page that can be used on its own or navigated to within a Frame.
/// </summary>
public sealed partial class MainPage : Page
{
private IrisModel _iris_model;
public MainPage()
{
this.InitializeComponent();
_iris_model = new IrisModel();
#pragma warning disable CS4014 // Because this call is not awaited, execution of the current method continues before the call is completed
_iris_model.Initialize();
#pragma warning restore CS4014 // Because this call is not awaited, execution of the current method continues before the call is completed
}
private void sepal_length_input_ValueChanged(object sender, RangeBaseValueChangedEventArgs e)
{
if (_iris_model != null)
{
_iris_model.Sepal_Length = (float)sepal_length_input.Value / 10.0f;
model_output.Text = _iris_model.Evaluate();
}
}
private void sepal_width_input_ValueChanged(object sender, RangeBaseValueChangedEventArgs e)
{
if (_iris_model != null)
{
_iris_model.Sepal_Width = (float)sepal_width_input.Value / 10.0f;
model_output.Text = _iris_model.Evaluate();
}
}
private void petal_length_input_ValueChanged(object sender, RangeBaseValueChangedEventArgs e)
{
if (_iris_model != null)
{
_iris_model.Petal_Length = (float)petal_length_input.Value / 10.0f;
model_output.Text = _iris_model.Evaluate();
}
}
private void petal_width_input_ValueChanged(object sender, RangeBaseValueChangedEventArgs e)
{
if (_iris_model != null)
{
_iris_model.Petal_Width = (float)petal_width_input.Value / 10.0f;
model_output.Text = _iris_model.Evaluate();
}
}
}
}
Avvia l'applicazione
A questo punto è possibile avviare l'applicazione e visualizzare i risultati.
Abilitare la modalità sviluppatore e testare l'applicazione da Visual Studio. Assicurarsi che i menu a discesa nella barra degli strumenti superiore siano impostati su Debug
. Impostare Solution Platform su x64 per eseguire il progetto nel computer locale se il dispositivo è a 64 bit o x86 se è a 32 bit.
L'interfaccia utente grafica dell'app include quattro dispositivi di scorrimento per modificare l'input dei parametri necessari. Qualsiasi modifica nell'input genererà un nuovo output basato sull'algoritmo di stima. L'output viene visualizzato sotto i dispositivi di scorrimento di input.
Si può notare che dato l'input di lunghezza sepale = 40mm, larghezza sepale = 50, lunghezza petalo = 75 e larghezza petalo = 15, l'app ha generato l'input di tipo Iris-versicolor!
Riepilogo
È stata appena creata la prima app di Windows Machine Learning, dalla creazione del modello alla corretta esecuzione.
Risorse aggiuntive
Per altre informazioni sugli argomenti presentati in questa esercitazione, vedere le risorse seguenti:
- Strumenti di Windows ML: altre informazioni su strumenti come dashboard di Windows ML, WinMLRunner e generatore di codice di Windows ML mglen .
- Modello ONNX: altre informazioni sul formato ONNX.
- Prestazioni e memoria di Windows ML: altre informazioni su come gestire le prestazioni delle app con Windows ML.
- Informazioni di riferimento sulle API di Windows Machine Learning: altre informazioni sulle tre aree delle API di Windows ML.