Ios UIImage通过像素循环效率很低?

Ios UIImage通过像素循环效率很低?,ios,arrays,swift,uiimage,Ios,Arrays,Swift,Uiimage,目前,我正在使用此方法循环遍历每个像素,并根据RGB值将值插入3D数组。我的程序的其他部分需要这个数组,但是它非常慢。当你在一张50 x 50的图片上运行时,它几乎是即时的,但一旦你开始进入数百x数百,它就需要很长的时间才能达到应用程序无用的程度。有人对如何加快我的方法有什么想法吗 @IBAction func convertImage(sender: AnyObject) { if let image = myImageView.image { var pixelDa

目前,我正在使用此方法循环遍历每个像素,并根据RGB值将值插入3D数组。我的程序的其他部分需要这个数组,但是它非常慢。当你在一张50 x 50的图片上运行时,它几乎是即时的,但一旦你开始进入数百x数百,它就需要很长的时间才能达到应用程序无用的程度。有人对如何加快我的方法有什么想法吗

@IBAction func convertImage(sender: AnyObject) {
    if let image = myImageView.image {

        var pixelData = CGDataProviderCopyData(CGImageGetDataProvider(image.CGImage))
        var data: UnsafePointer<UInt8> = CFDataGetBytePtr(pixelData)

        let height = Int(image.size.height)
        let width = Int(image.size.width)
        var zArry = [Int](count:3, repeatedValue: 0)
        var yArry = [[Int]](count:width, repeatedValue: zArry)
        var xArry = [[[Int]]](count:height, repeatedValue: yArry)

        for (var h = 0; h < height; h++) {
            for (var w = 0; w < width; w++) {
                 var pixelInfo: Int = ((Int(image.size.width) * Int(h)) + Int(w)) * 4
                var rgb = 0
                xArry[h][w][rgb] = Int(data[pixelInfo])
                rgb++
                xArry[h][w][rgb] = Int(data[pixelInfo+1])
                rgb++
                xArry[h][w][rgb] = Int(data[pixelInfo+2])
                }
        }
        println(xArry[20][20][1])
    }
}
@IBAction func convertImage(发件人:AnyObject){
如果让image=myImageView.image{
var pixelData=CGDataProviderCopyData(CGImageGetDataProvider(image.CGImage))
变量数据:UnsafePointer=CFDataGetBytePtr(pixelData)
let height=Int(image.size.height)
let width=Int(image.size.width)
var zArry=[Int](计数:3,重复值:0)
var yArry=[[Int]](计数:宽度,重复值:zArry)
var xArry=[[[Int]]](计数:高度,重复值:yArry)
对于(var h=0;h
也许有一种方法可以将UIImage转换为不同类型的图像并创建像素阵列。我愿意接受所有建议。谢谢


目标:目标是使用数组修改所有像素的RGB值,并使用修改后的像素创建新图像。我试着简单地循环所有像素而不存储它们,并将它们修改成一个新的数组来创建图像,但得到了相同的性能问题。

更新:

在无数次尝试之后,我意识到我正在调试配置上进行测试

切换到发布,现在速度快多了

Swift在调试配置上似乎慢了很多倍

现在,您的代码与我的优化版本之间的差异快了好几倍

似乎使用
image.size.width
而不是局部变量
width
会大大降低速度

原创

我试图对其进行一些优化,并得出以下结论:

@IBAction func convertImage () {

    if let image = UIImage(named: "test") {

        let pixelData = CGDataProviderCopyData(CGImageGetDataProvider(image.CGImage))
        let data: UnsafePointer<UInt8> = CFDataGetBytePtr(pixelData)

        let height = Int(image.size.height)
        let width = Int(image.size.width)
        let zArry = [Int](count:3, repeatedValue: 0)
        let yArry = [[Int]](count:width, repeatedValue: zArry)
        let xArry = [[[Int]]](count:height, repeatedValue: yArry)

        for (index, value) in xArry.enumerate() {
            for (index1, value1) in value.enumerate() {
                for (index2, var value2) in value1.enumerate() {

                    let pixelInfo: Int = ((width * index) + index1) * 4 + index2

                    value2 = Int(data[pixelInfo])
                }
            }
        }
    }
}
@IBAction func convertImage(){
如果let image=UIImage(名为“test”){
设pixelData=CGDataProviderCopyData(CGImageGetDataProvider(image.CGImage))
let data:UnsafePointer=CFDataGetBytePtr(像素数据)
let height=Int(image.size.height)
let width=Int(image.size.width)
让zArry=[Int](计数:3,重复值:0)
让yArry=[[Int]](计数:宽度,重复值:zArry)
让xArry=[[[Int]]](计数:高度,重复值:yArry)
对于xArry.enumerate()中的(索引、值){
对于value.enumerate()中的(index1,value1){
对于value1.enumerate()中的(index2,var value2){
让pixelInfo:Int=((宽度*索引)+index1)*4+index2
值2=Int(数据[pixelInfo])
}
}
}
}
}
然而,在我的测试中,这仅仅快了15%。你需要的是快几个数量级

另一种想法是在需要时直接使用数据对象,而不创建如下数组:

let image = UIImage(named: "test")!

let pixelData = CGDataProviderCopyData(CGImageGetDataProvider(image.CGImage))
let data: UnsafePointer<UInt8> = CFDataGetBytePtr(pixelData)

let width = Int(image.size.width)

// value for [x][y][z]
let value = Int(data[((width * x) + y) * 4 + z])
let image=UIImage(名为:“test”)!
设pixelData=CGDataProviderCopyData(CGImageGetDataProvider(image.CGImage))
let data:UnsafePointer=CFDataGetBytePtr(像素数据)
let width=Int(image.size.width)
//[x][y][z]的值
设值=Int(数据[(宽度*x+y)*4+z])

您没有说明如何在应用程序中使用此阵列,但我觉得,即使您找到了一种更快创建此阵列的方法,您在尝试使用它时也会遇到另一个问题,因为这也需要很长时间。

只是一个建议,但您可以从解开rgb循环开始。好的,该循环现在已解开。还是很慢。无论如何,感谢您的建议,因为它可能有助于稍微加快速度。我的一个朋友可能会建议使用霓虹灯指令(单指令/多数据)来并行读取数据,但我不知道细节,可能无法从swift(相对于C/Objective-C)执行此操作。如果它至少可以作为一个指针……您还可以尝试在Xcode中使用评测来查看哪个部分实际速度慢,了解您需要优化什么。这个问题是针对OSX的,但解决方案在类似问题上对我帮助很大,也许它会帮助您:如果您用加法代替乘法,您将获得巨大的性能提升。通过
repeatedValue:
进行初始化也是性能损失。乘法所花费的时间约为1%。初始化时间似乎可以忽略不计。我也将在原始帖子中提到这一点,但目标是使用数组修改所有像素的RGB值,并使用修改后的像素创建新图像。我试着简单地循环所有的像素而不存储它们,然后将它们修改成一个新的数组来创建一个图像,但是得到了同样的性能问题。正是这个嵌套的循环让你死掉了。您是否可以尝试制作一个哈希映射,将复杂性降低到O(1)或O(n),而不是O(n^2 log n)。或者甚至尝试使用deepMap风格的函数,这里有一个关于深度映射的线程,将其转换为Swift应该很简单:另一个想法是使用线程来更快地处理数据,只需划分数据的大小(应该是O(1)来调用大小),然后生成X多个线程来处理0-10000、10000-20000范围内的像素,20000-30000等。。