Quickstart iOS¶
Avertissement
Le SDK expérimental Flower pour iOS n’est pas compatible avec la dernière version de Flower. Le support iOS est actuellement réécrit et sera publié en 2025.
Ce tutoriel rapide est conservé à des fins historiques et sera mis à jour une fois que le nouveau SDK iOS sera publié.
In this tutorial we will learn how to train a Neural Network on MNIST using Flower and CoreML on iOS devices.
Tout d’abord, pour lancer le serveur Python de Flower, il est recommandé de créer un environnement virtuel et de faire tourner tout dans un virtualenv. Pour la mise en œuvre client Flower sur iOS, il est recommandé d’utiliser Xcode comme IDE.
Our example consists of one Python server and two iPhone clients that all have the same model.
Clients are responsible for generating individual weight updates for the model based on their local datasets. These updates are then sent to the server which will aggregate them to produce a better model. Finally, the server sends this improved version of the model back to each client. A complete cycle of weight updates is called a round.
Now that we have a rough idea of what is going on, let’s get started to setup our Flower server environment. We first need to install Flower. You can do this by using pip:
$ pip install flwr[simulation]
Ou uv:
$ uv add flwr
Client de Flower¶
Now that we have all our dependencies installed, let’s run a simple distributed training using CoreML as our local training pipeline and MNIST as our dataset. For simplicity reasons we will use the complete Flower client with CoreML, that has been implemented and stored inside the Swift SDK. The client implementation can be seen below:
/// Parses the parameters from the local model and returns them as GetParametersRes struct
///
/// - Returns: Parameters from the local model
public func getParameters() -> GetParametersRes {
let parameters = parameters.weightsToParameters()
let status = Status(code: .ok, message: String())
return GetParametersRes(parameters: parameters, status: status)
}
/// Calls the routine to fit the local model
///
/// - Returns: The result from the local training, e.g., updated parameters
public func fit(ins: FitIns) -> FitRes {
let status = Status(code: .ok, message: String())
let result = runMLTask(configuration: parameters.parametersToWeights(parameters: ins.parameters), task: .train)
let parameters = parameters.weightsToParameters()
return FitRes(parameters: parameters, numExamples: result.numSamples, status: status)
}
/// Calls the routine to evaluate the local model
///
/// - Returns: The result from the evaluation, e.g., loss
public func evaluate(ins: EvaluateIns) -> EvaluateRes {
let status = Status(code: .ok, message: String())
let result = runMLTask(configuration: parameters.parametersToWeights(parameters: ins.parameters), task: .test)
return EvaluateRes(loss: Float(result.loss), numExamples: result.numSamples, status: status)
}
Créeons un nouveau projet d’application dans Xcode et ajoutez flwr comme dépendance à votre projet. Pour notre application, nous stockerons la logique de notre application dans FLiOSModel.swift et les éléments UI dans ContentView.swift. Nous nous concentrerons davantage sur FLiOSModel.swift dans ce tutoriel rapide. Veuillez vous référer au full code example pour en savoir plus sur l’application.
Importez les packages Flower et CoreML liés dans FLiOSModel.swift:
import Foundation
import CoreML
import flwr
Ajoutez ensuite le mlmodel au projet simplement en traînant-déposant, le mlmodel sera emballé à l’intérieur de l’application lors du déploiement sur votre appareil iOS. Nous avons besoin de passer l’URL pour accéder au mlmodel et exécuter les processus d’apprentissage par machine CoreML, cela peut être récupéré en appelant la fonction Bundle.main.url. Pour le jeu de données MNIST, nous avons besoin de le prétraiter en objet MLBatchProvider. Le prétraitement est effectué à l’intérieur de DataLoader.swift:
// prepare train dataset
let trainBatchProvider = DataLoader.trainBatchProvider() { _ in }
// prepare test dataset
let testBatchProvider = DataLoader.testBatchProvider() { _ in }
// load them together
let dataLoader = MLDataLoader(trainBatchProvider: trainBatchProvider,
testBatchProvider: testBatchProvider)
Puisque CoreML ne permet pas aux paramètres du modèle d’être vus avant l’entraînement, et accéder aux paramètres du modèle pendant ou après l’entraînement peut uniquement être fait en spécifiant le nom de la couche, nous avons besoin de connaître cette information à l’avance, grâce à regarder à la spécification du modèle, qui sont écrites sous forme de fichiers proto. La mise en œuvre peut être vue dans MLModelInspect:
Après avoir obtenu toutes les informations nécessaires, créons notre client Flower.
let compiledModelUrl = try MLModel.compileModel(at: url)
// inspect the model to be able to access the model parameters
// to access the model we need to know the layer name
// since the model parameters are stored as key value pairs
let modelInspect = try MLModelInspect(serializedData: Data(contentsOf: url))
let layerWrappers = modelInspect.getLayerWrappers()
self.mlFlwrClient = MLFlwrClient(layerWrappers: layerWrappers,
dataLoader: dataLoader,
compiledModelUrl: compiledModelUrl)
Puis commencez le client Flower gRPC et commencez à communiquer avec le serveur en passant notre client Flower à la fonction startFlwrGRPC:
self.flwrGRPC = FlwrGRPC(serverHost: hostname, serverPort: port)
self.flwrGRPC.startFlwrGRPC(client: self.mlFlwrClient)
C’est tout pour le client. Nous n’avons qu’à mettre en œuvre Client ou appeler la fonction fournie MLFlwrClient et appelez startFlwrGRPC(). L’attribut hostname et port indique au client quel serveur se connecter. Cela peut être fait en entrant l’hôte et le port dans l’application avant de cliquer sur le bouton d’exécution pour démarrer le processus d’apprentissage fédéré.
Serveur de Flower¶
Pour des charges de travail simples, nous pouvons démarrer un serveur Flower et laisser toutes les possibilités de configuration à leurs valeurs par défaut. Dans un fichier nommé server.py, importez Flower et démarrez le serveur :
import flwr as fl
fl.server.start_server(config=fl.server.ServerConfig(num_rounds=3))
Entraîne le modèle, fédéré !¶
Le client et le serveur étant prêts, nous pouvons maintenant tout exécuter et voir l’apprentissage fédéré en action. Les systèmes FL ont généralement un serveur et plusieurs clients. Nous devons donc commencer par démarrer le serveur :
$ python server.py
Once the server is running we can start the clients in different terminals. Build and run the client through your Xcode, one through Xcode Simulator and the other by deploying it to your iPhone. To see more about how to deploy your app to iPhone or Simulator visit here.
Félicitations ! Vous avez réussi à créer et à lancer votre premier système d’apprentissage fédéré sur votre appareil iOS. Le code complet source code pour cet exemple peut être trouvé dans examples/ios.