简体   繁体   English

如何释放UIImageView的内存(Swift)

[英]How to release memory for UIImageView (Swift)

I got a problem with UIImage. 我遇到了UIImage问题。 I've manually added UIImageView objects to a scroll view. 我已经手动将UIImageView对象添加到滚动视图。 The problem is : when I have more than 50 images, memory will increase to around 200MB, and the app will be crash on iphone 4 or 4s. 问题是:当我有超过50张图像时,内存将增加到200MB左右,并且该应用程序将在iPhone 4或4s上崩溃。 I want to release memory for images that is not in visible part when I receive Memory Warning to prevent crashing but I don't know how to release them with Swift. 我想为收到内存警告以防止崩溃的不可见部分图像释放内存,但我不知道如何使用Swift释放它们。 Help me please. 请帮帮我。

override func didReceiveMemoryWarning() {
    super.didReceiveMemoryWarning()

    // Dispose of any resources that can be recreated.
}

func loadImage(index:Int){
if self.imgPaths.count == 0 {
    println("Has not data")
    actInd.stopAnimating()
    return
}
var imgURL: NSURL = NSURL(string: self.imgPaths[index].stringByTrimmingCharactersInSet(.whitespaceAndNewlineCharacterSet()))!
let width:CGFloat = self.view.bounds.width
let height:CGFloat = self.view.bounds.height
var view:UIView = UIView(frame: CGRectMake(0, 0, width, height));

if let imgObj = self.dicData[index] {

}
else
{
println("imgURL \(imgURL)")
let request: NSURLRequest = NSURLRequest(URL: imgURL)
NSURLConnection.sendAsynchronousRequest(request, queue: NSOperationQueue.mainQueue(), completionHandler: {(response: NSURLResponse!,data: NSData!,error: NSError!) -> Void in
    if error == nil {
        let imgItem = UIImage(data: data)!

        var te :Float = self.imgPaths.count > 0 ? Float(index  + 1) / Float(self.imgPaths.count) : 1
        self.progressView.setProgress(te, animated: true)

        if let imgObj = self.dicData[index] {

            if index < self.imgPaths.count - 1
            {
                var nextIndex:Int = index + 1
                self.loadImage(nextIndex)
            }
            if(index == self.imgPaths.count - 1)
            {
                if self.currentImageIndex > 0
                {
                    self.isAddedFirstImg = true
                }
                if !self.isAddedFirstImg
                {
                    self.scrollViews[0].zoomScale = self.zoomScales[0]
                    self.view.insertSubview(self.scrollViews[0], belowSubview: self.tabBar.viewWithTag(77)!)
                    self.isAddedFirstImg = true
                }

                self.actInd.stopAnimating()
                println("loaded image")
            }
        }
        else
        {
            self.dicData[index] = UIImageView(image: imgItem)

            self.dicData[index]?.frame = CGRect(origin: CGPointMake(0.0, 0.0), size:imgItem.size)

            // 2
            self.scrollViews[index].addSubview(self.dicData[index]!)
            self.scrollViews[index].contentSize = imgItem.size

            // 3
            var doubleTapRecognizer = UITapGestureRecognizer(target: self, action: "scrollViewDoubleTapped:")
            doubleTapRecognizer.numberOfTapsRequired = 2
            doubleTapRecognizer.numberOfTouchesRequired = 1
            self.scrollViews[index].addGestureRecognizer(doubleTapRecognizer)

            var singleTapRecognizer = UITapGestureRecognizer(target: self, action: "scrollViewSingleTapped:")
            singleTapRecognizer.numberOfTapsRequired = 1
            singleTapRecognizer.numberOfTouchesRequired = 1
            self.scrollViews[index].addGestureRecognizer(singleTapRecognizer)

            var swipeRight = UISwipeGestureRecognizer(target: self, action: "respondToSwipeGesture:")
            swipeRight.direction = UISwipeGestureRecognizerDirection.Right
            self.scrollViews[index].addGestureRecognizer(swipeRight)

            var swipeLeft = UISwipeGestureRecognizer(target: self, action: "respondToSwipeGesture:")
            swipeLeft.direction = UISwipeGestureRecognizerDirection.Left
            self.scrollViews[index].addGestureRecognizer(swipeLeft)

            // 4
            var scrollViewFrame = self.scrollViews[index].frame
            var scaleWidth = scrollViewFrame.size.width / self.scrollViews[index].contentSize.width
            var scaleHeight = scrollViewFrame.size.height / self.scrollViews[index].contentSize.height
            var minScale = min(scaleWidth, scaleHeight)
            self.zoomScales[index] = minScale
            self.scrollViews[index].minimumZoomScale = minScale

            // 5
            self.scrollViews[index].maximumZoomScale = 1.0
            self.scrollViews[index].delegate = self

            // 6
            self.centerScrollViewContents(index)

            dispatch_async(dispatch_get_main_queue(), {
                println("downloaded image index: \(index) CH.\(self.chapterID)")
                if(index == 0)
                {
                    self.scrollViews[0].zoomScale = self.zoomScales[0]
                    self.view.insertSubview(self.scrollViews[0], belowSubview: self.tabBar.viewWithTag(77)!)
                    self.actInd.stopAnimating()
                }

                if index < self.imgPaths.count - 1 && !self.stopDownload
                {
                    var nextIndex:Int = index + 1
                    self.loadImage(nextIndex)
                }
                if(index == self.imgPaths.count - 1)
                {
                    if self.currentImageIndex > 0
                    {
                        self.isAddedFirstImg = true
                    }
                    if !self.isAddedFirstImg
                    {
                        self.scrollViews[0].zoomScale = self.zoomScales[0]
                        self.view.insertSubview(self.scrollViews[0], belowSubview: self.tabBar.viewWithTag(77)!)
                        self.isAddedFirstImg = true
                    }

                    self.actInd.stopAnimating()
                    println("loaded image")
                }
            })
        }
    }
    else {
        println("Error: \(error.localizedDescription)")
    }
})
}

} }

Swift uses ARC (Automatic Reference Counting) to manage memory. Swift使用ARC(自动引用计数)来管理内存。 To free something from memory, you must remove all references to that object. 要从内存中释放某些内容,必须删除对该对象的所有引用。 ARC maintains a count of the number of places that hold a reference to the object, and when that count reaches 0, the memory is freed. ARC会维护一个保存对对象的引用的位置数,当该计数达到0时,将释放内存。

In your case, your imageViews are stored in self.dicData[index] and they are added as subviews of self.scrollViews[index] . 在您的情况下,您的self.dicData[index]存储在self.dicData[index]并将它们作为self.scrollViews[index]子视图添加。 You will need to remove the imageView from its superview and from self.dicData . 您将需要从其self.dicData视图和self.dicData删除self.dicData Once you do that, the memory will be freed. 完成后,内存将被释放。

If you have the index of the imageView you want to free: 如果您有要释放的imageView的index ,请执行以下操作:

self.dicData[index]?.removeFromSuperview()
self.dicData[index] = nil

in swift there is really good tool called "lazy" you might wanted to study about lazy var its very handy when it comes down to the images and tableview (for your instance collectionview) 快速有一个非常好的工具叫做“ lazy”,您可能想研究lazy var,当它涉及到图像和表格视图时(对于您的实例collectionview),它非常方便

you will see a huge difference when its used from custom cell. 您将从自定义单元格中使用它时会看到巨大的差异。 create a imageview eg lazy var imageViewer:UIImageView my app was at about 150mb 200mb memory now its at 40~60mb try it! 创建一个imageview,例如lazy var imageViewer:UIImageView我的应用程序大约在150mb 200mb的内存上,现在它在40〜60mb尝试一下!

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM