CIImage内存未释放 [英] CIImage memory not released
问题描述
我正在尝试拍摄一系列图像,同时混合X个图像并生成一个新图像.这是我必须完成的代码:
I am trying to take a sequence of images, blend X images at the time and produce a new image. This is the code I have to accomplish this:
static func blendImages(blendFrames: Int, blendMode: CIImage.BlendMode, imagePaths: [URL], completion: @escaping (_ progress: Double) -> Void) {
var currentIndex = 0
while currentIndex + blendFrames < imagePaths.count {
let currentSubset = Array(imagePaths[currentIndex..<(currentIndex + blendFrames)])
var currentSubsetIndex = 0
var firstImage: CIImage?
while currentSubset.count > currentSubsetIndex + 1 {
if firstImage == nil { firstImage = CIImage(contentsOf: currentSubset[currentSubsetIndex]) } //First image allocated in memory
if let secondImage = CIImage(contentsOf: currentSubset[currentSubsetIndex + 1]) {//Second image allocated in memory
firstImage = firstImage?.blend(with: secondImage, blendMode: blendMode)
} //Would expect secondImage to be freed from memory at this point, but it does not happen
currentSubsetIndex += 1
}
if let finalImage = firstImage {
let bitMapRep = NSBitmapImageRep(ciImage: finalImage)
let data = bitMapRep.representation(using: .jpeg, properties: [:])
do {
try data?.write(to: URL(fileURLWithPath: "Final-" + String(format: "%03d", currentIndex) + ".jpg"))
} catch let error as NSError {
print("Failed to write to disk: \(error)")
}
}
firstImage = nil //Would expect firstImage to be freed from memory at this point (or at beginning of next cycle in while-loop), but it does not happen
currentIndex += 1
}
}
还有CIImage的blend
函数的代码
And the code for CIImage's blend
function
extension CIImage {
enum BlendMode: String {
case Lighten = "CILightenBlendMode"
case Darken = "CIDarkenBlendMode"
}
func blend(with image: CIImage, blendMode: BlendMode) -> CIImage? {
let filter = CIFilter(name: blendMode.rawValue)!
filter.setDefaults()
filter.setValue(self, forKey: "inputImage")
filter.setValue(image, forKey: "inputBackgroundImage")
return filter.outputImage
}
}
如代码注释中所述,我希望在创建它们的作用域末尾释放在firstImage和secondImage中分配的内存.由于它们都是在while循环中创建的,所以我希望它们在该循环结束时将其释放,但是,这似乎没有发生.但是这里没有内存泄漏,因为当blendImages
函数完成时,内存已被适当地释放(但是,这太迟了,因为代码可以运行成百上千个图像,从而使该应用程序在使用之前消耗了数TB的数据)它被释放了).
如果有人能看到我的代码中的缺陷以及如何提高其内存效率,那将不胜感激.
As detailed in the comments in the code I would expect the memory allocated in firstImage and secondImage to be freed up at the end of the scope they are created in. Since they are both created within a while-loop I would expect them to be freed up at the end of that loop, however, that appears not to happen. But there is no memory leak here, because when the blendImages
function finishes the memory is appropriately freed up (however, this is too late as the code could run through hundreds or thousands of images, making the app consume several TBs of data before it is freed up).
If anyone can see the flaw in my code and how to make it more memory-efficient that would be very much appreciated.
推荐答案
您应使用 autoreleasepool
函数可强制释放其作用域内的对象.此功能将帮助您更精确地管理内存占用.
You should use the autoreleasepool
function to force the release of the objects inside its scope. This function will help you to manage the memory footprint more precisely.
static func blendImages(blendFrames: Int, blendMode: CIImage.BlendMode, imagePaths: [URL], completion: @escaping (_ progress: Double) -> Void) {
var currentIndex = 0
while currentIndex + blendFrames < imagePaths.count {
autorelease {
// your code
}
currentIndex += 1
}
}
您可以查看此帖子以获得更多信息.
You can check this post to have more informations.
这篇关于CIImage内存未释放的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!