Xamarin.iOS의 CoreML 소개
CoreML은 iOS에 기계 학습을 제공합니다. 앱은 학습된 기계 학습 모델을 활용하여 문제 해결에서 이미지 인식에 이르기까지 모든 종류의 작업을 수행할 수 있습니다.
이 소개에서는 다음을 다룹니다.
CoreML 시작
다음 단계에서는 iOS 프로젝트에 CoreML을 추가하는 방법을 설명합니다.
1. 프로젝트에 CoreML 모델 추가
CoreML 모델(.mlmodel 확장이 있는 파일)을 프로젝트의 Resources 디렉터리에 추가합니다.
모델 파일의 속성에서 빌드 작업은 CoreMLModel로 설정됩니다. 즉, 애플리케이션이 빌드될 때 .mlmodelc 파일로 컴파일됩니다.
2. 모델 로드
정적 메서드를 사용하여 모델을 로드합니다 MLModel.Create
.
var assetPath = NSBundle.MainBundle.GetUrlForResource("NameOfModel", "mlmodelc");
model = MLModel.Create(assetPath, out NSError error1);
3. 매개 변수 설정
모델 매개 변수는 구현하는 컨테이너 클래스를 사용하여 전달됩니다 IMLFeatureProvider
.
기능 공급자 클래스는 문자열 및 s의 사전처럼 동작하며 MLFeatureValue
, 각 기능 값은 단순 문자열 또는 숫자, 배열 또는 데이터 또는 이미지를 포함하는 픽셀 버퍼일 수 있습니다.
단일 값 기능 공급자에 대한 코드는 다음과 같습니다.
public class MyInput : NSObject, IMLFeatureProvider
{
public double MyParam { get; set; }
public NSSet<NSString> FeatureNames => new NSSet<NSString>(new NSString("myParam"));
public MLFeatureValue GetFeatureValue(string featureName)
{
if (featureName == "myParam")
return MLFeatureValue.FromDouble(MyParam);
return MLFeatureValue.FromDouble(0); // default value
}
이와 같은 클래스를 사용하면 CoreML에서 이해하는 방식으로 입력 매개 변수를 제공할 수 있습니다. 기능의 이름(예: myParam
코드 예제)은 모델이 기대하는 이름과 일치해야 합니다.
4. 모델 실행
모델을 사용하려면 기능 공급자를 인스턴스화하고 매개 변수를 설정한 다음 메서드를 GetPrediction
호출해야 합니다.
var input = new MyInput {MyParam = 13};
var outFeatures = model.GetPrediction(inputFeatures, out NSError error2);
5. 결과 추출
예측 결과는 outFeatures
다음 예제와 같이 각 출력 매개 변수의 이름(예: theResult
)을 사용하여 GetFeatureValue
출력 값에 액세스할 수 있는 인스턴스IMLFeatureProvider
이기도 합니다.
var result = outFeatures.GetFeatureValue("theResult").DoubleValue; // eg. 6227020800
Vision Framework에서 CoreML 사용
CoreML을 Vision 프레임워크와 함께 사용하여 셰이프 인식, 개체 식별 및 기타 작업과 같은 이미지 작업을 수행할 수도 있습니다.
아래 단계에서는 CoreML과 Vision을 함께 사용하는 방법을 설명합니다. 이 샘플은 Vision 프레임워크의 사각형 인식 과 MNINSTClassifier CoreML 모델을 결합하여 사진의 필기 숫자를 식별합니다.
1. Vision CoreML 모델 만들기
CoreML 모델 MNISTClassifier 가 로드된 다음, 모델을 Vision 작업에 사용할 수 있도록 래핑 VNCoreMLModel
합니다. 또한 이 코드는 두 가지 Vision 요청을 만듭니다. 먼저 이미지에서 사각형을 찾은 다음 CoreML 모델을 사용하여 사각형을 처리하기 위한 것입니다.
// Load the ML model
var bundle = NSBundle.MainBundle;
var assetPath = bundle.GetUrlForResource("MNISTClassifier", "mlmodelc");
NSError mlErr, vnErr;
var mlModel = MLModel.Create(assetPath, out mlErr);
var model = VNCoreMLModel.FromMLModel(mlModel, out vnErr);
// Initialize Vision requests
RectangleRequest = new VNDetectRectanglesRequest(HandleRectangles);
ClassificationRequest = new VNCoreMLRequest(model, HandleClassification);
클래스는 여전히 아래의 HandleRectangles
3단계와 HandleClassification
4단계에 표시된 Vision 요청에 대한 메서드와 메서드를 구현해야 합니다.
2. Vision 처리 시작
다음 코드는 요청 처리를 시작합니다. CoreMLVision 샘플에서 이 코드는 사용자가 이미지를 선택한 후에 실행됩니다.
// Run the rectangle detector, which upon completion runs the ML classifier.
var handler = new VNImageRequestHandler(ciImage, uiImage.Orientation.ToCGImagePropertyOrientation(), new VNImageOptions());
DispatchQueue.DefaultGlobalQueue.DispatchAsync(()=>{
handler.Perform(new VNRequest[] {RectangleRequest}, out NSError error);
});
이 처리기는 1단계에서 만든 Vision 프레임워크 VNDetectRectanglesRequest
에 전달 ciImage
합니다.
3. Vision 처리 결과 처리
사각형 검색이 완료되면 첫 번째 사각형을 추출하도록 이미지를 자르는 메서드를 실행하고 HandleRectangles
, 사각형 이미지를 회색조로 변환하고, 분류를 위해 CoreML 모델에 전달합니다.
이 메서드에 전달된 매개 변수는 request
Vision 요청의 세부 정보를 포함하고 메서드를 GetResults<VNRectangleObservation>()
사용하여 이미지에 있는 사각형 목록을 반환합니다. 첫 번째 사각형 observations[0]
이 추출되어 CoreML 모델에 전달됩니다.
void HandleRectangles(VNRequest request, NSError error) {
var observations = request.GetResults<VNRectangleObservation>();
// ... omitted error handling ...
var detectedRectangle = observations[0]; // first rectangle
// ... omitted cropping and greyscale conversion ...
// Run the Core ML MNIST classifier -- results in handleClassification method
var handler = new VNImageRequestHandler(correctedImage, new VNImageOptions());
DispatchQueue.DefaultGlobalQueue.DispatchAsync(() => {
handler.Perform(new VNRequest[] {ClassificationRequest}, out NSError err);
});
}
다음 ClassificationRequest
단계에서 정의된 메서드를 HandleClassification
사용하도록 1단계에서 초기화되었습니다.
4. CoreML 처리
이 메서드에 전달된 매개 변수는 request
CoreML 요청의 세부 정보를 포함하며, 메서드를 GetResults<VNClassificationObservation>()
사용하여 신뢰도(가장 높은 신뢰도 먼저)로 정렬된 가능한 결과 목록을 반환합니다.
void HandleClassification(VNRequest request, NSError error){
var observations = request.GetResults<VNClassificationObservation>();
// ... omitted error handling ...
var best = observations[0]; // first/best classification result
// render in UI
DispatchQueue.MainQueue.DispatchAsync(()=>{
ClassificationLabel.Text = $"Classification: {best.Identifier} Confidence: {best.Confidence * 100f:#.00}%";
});
}