识别照片时的时间差Swift
Timing difference when recognizing photos Swift
我创建了一个识别照片中花朵的应用程序。照片可以来自画廊或用相机拍摄。我有功能:
func detectFlower(image: CIImage,completion: @escaping (_ getString:String?,_ error:Error?,_ getDouble:Double?,_ getArray:Array<VNConfidence>?,_ getArray:Array<String>?)-> Void) {
guard let model = try? VNCoreMLModel(for: NewFlowersModel().model) else {
fatalError("Cannot import a model.")
}
let methodStart = Date()
let request = VNCoreMLRequest(model: model) { (request, error) in
let classifiedNameOfFlower = request.results?.first as? VNClassificationObservation
let classifiedValues = request.results as? [VNClassificationObservation]
let methodFinish = Date()
let nameOfFlower = String(classifiedNameOfFlower?.identifier ?? "Unexpected type")
let executionTime = methodFinish.timeIntervalSince(methodStart)
let classificationConfidences = classifiedValues?.prefix(10).map {
([=11=].confidence)
}
let classificationIdentifiers = classifiedValues?.prefix(10).map {
([=11=].identifier)
}
completion(nameOfFlower,nil,executionTime, classificationConfidences, classificationIdentifiers)
}
let handler = VNImageRequestHandler(ciImage: image)
do {
try handler.perform([request])
} catch {
print(error)
completion(nil, error, nil, nil, nil)
}
}
用于识别。其中有两个常量let methodStart = Date()
和let methodFinish = Date()
用于测量时间。稍后在代码中有一个计算差异的常量 let executionTime = methodFinish.timeIntervalSince(methodStart)
.
我注意到一个奇怪的依赖 - 当我 运行 应用程序时,第一次扫描 returns 一个时间差,例如0.395959 秒。下一次扫描 returns 时间要短得多,例如 0.033615 秒。这可能是什么结果?是什么原因造成的时间差,第一次扫描,总是这个时间最长?
这段时间大部分时间可能是从磁盘加载模型。每次进行检测时,您都在重新创建整个模型:
guard let model = try? VNCoreMLModel(for: NewFlowersModel().model) else { ... }
第一次这样做时,您需要从磁盘加载大量数据。之后,其中大部分将被缓存,但这通常不是正确的方法,因为您仍然在重新创建数据结构上浪费大量精力。
您要做的是只创建一次模型和请求,可能是在应用程序启动期间,或者当您来到此屏幕时,或者在您认为用户需要 ML 引擎时。将其存储在 属性 或共享对象中。然后,每次获得新图像时,只需创建 VNImageRequestHandler
并执行它即可。
我创建了一个识别照片中花朵的应用程序。照片可以来自画廊或用相机拍摄。我有功能:
func detectFlower(image: CIImage,completion: @escaping (_ getString:String?,_ error:Error?,_ getDouble:Double?,_ getArray:Array<VNConfidence>?,_ getArray:Array<String>?)-> Void) {
guard let model = try? VNCoreMLModel(for: NewFlowersModel().model) else {
fatalError("Cannot import a model.")
}
let methodStart = Date()
let request = VNCoreMLRequest(model: model) { (request, error) in
let classifiedNameOfFlower = request.results?.first as? VNClassificationObservation
let classifiedValues = request.results as? [VNClassificationObservation]
let methodFinish = Date()
let nameOfFlower = String(classifiedNameOfFlower?.identifier ?? "Unexpected type")
let executionTime = methodFinish.timeIntervalSince(methodStart)
let classificationConfidences = classifiedValues?.prefix(10).map {
([=11=].confidence)
}
let classificationIdentifiers = classifiedValues?.prefix(10).map {
([=11=].identifier)
}
completion(nameOfFlower,nil,executionTime, classificationConfidences, classificationIdentifiers)
}
let handler = VNImageRequestHandler(ciImage: image)
do {
try handler.perform([request])
} catch {
print(error)
completion(nil, error, nil, nil, nil)
}
}
用于识别。其中有两个常量let methodStart = Date()
和let methodFinish = Date()
用于测量时间。稍后在代码中有一个计算差异的常量 let executionTime = methodFinish.timeIntervalSince(methodStart)
.
我注意到一个奇怪的依赖 - 当我 运行 应用程序时,第一次扫描 returns 一个时间差,例如0.395959 秒。下一次扫描 returns 时间要短得多,例如 0.033615 秒。这可能是什么结果?是什么原因造成的时间差,第一次扫描,总是这个时间最长?
这段时间大部分时间可能是从磁盘加载模型。每次进行检测时,您都在重新创建整个模型:
guard let model = try? VNCoreMLModel(for: NewFlowersModel().model) else { ... }
第一次这样做时,您需要从磁盘加载大量数据。之后,其中大部分将被缓存,但这通常不是正确的方法,因为您仍然在重新创建数据结构上浪费大量精力。
您要做的是只创建一次模型和请求,可能是在应用程序启动期间,或者当您来到此屏幕时,或者在您认为用户需要 ML 引擎时。将其存储在 属性 或共享对象中。然后,每次获得新图像时,只需创建 VNImageRequestHandler
并执行它即可。