iOS: helpfulness of didReceiveMemoryWarning:

前端 未结 4 2091
予麋鹿
予麋鹿 2020-12-05 11:47

I\'m at the part of my development process for tracking down crashing and memory leaks. As a strategy, do you put any NSLog messages or notifications of some such into

相关标签:
4条回答
  • 2020-12-05 12:21

    If the user left some apps open you will have very little memory at your disposal. So sometimes didReceiveMemoryWarning can be called by the system only after 1 MB of usage.

    The system calls this method on all your view controllers, if you place a NSLog in each of your view controllers, you will notice that.

    Then automatically the method viewDidUnload will be called by the system on all your view controllers (not dealloc). So you have to put all your deallocation instructions in there.

    You have to make a lot of experiments because if your app is complex you will face lot of crashes before managing it well.

    0 讨论(0)
  • 2020-12-05 12:24

    The purpose of didReceiveMemoryWarning is to give you a chance to free memory or pop views to avoid a crash. You will not receive it at any predictable point because it depends on what the user is doing. For example, if the user is listening to the iPod, there is less available memory and you will receive it sooner.

    The general rule of thumb is that you have about 8MB of RAM to work with. When you get close to that you can expect the event to be raised. If you are taking up that much RAM deliberately you should have a plan to do something about it.

    0 讨论(0)
  • 2020-12-05 12:26

    UPDATE As of iOS 6, UIViewController views are no longer unloaded in response to memory warnings. Instead just do your best to release any resources you can reasonably re-create (e.g. cached data) when didReceiveMemoryWarning is called.

    UPDATE
    I wrote my original answer when I was an angry young man; times have changed and basically, it's wrong.

    If you have an app with a single view controller and you receive a memory warning, there's not much you can do. But things change dramatically if you have multiple view controllers, because you can unload all the state associated with the non frontmost controllers. In fact [UIViewController didReceiveMemoryWarning] will prod you in the right direction by unloading your non-visible views for you (surprise!). When the frontmost view controller is dismissed, the underlying view is reloaded and at most the user should only be aware of a delay even though internally your app may have done a complete reboot.

    This is not some detail you can easily retrofit, you need to keep memory usage in mind from the beginning and design your multiview app into cleanly unloadable UIViewController pieces. In fact it's worth keeping your code compatible with the simulator just to use its memory warning feature.

    When memory is abundant, nothing is unloaded and everything is silky smooth, and when memory is low things keep working, albeit more slowly. Now I'd say that this solution to the finite memory problem is ideal.

    To take advantage of this memory parlour trick, overload the UIViewController methods viewDidLoad,viewDidUnload, and viewWillUnload (iOS5, useful if unloading state requires your view to still exist, e.g. if you don't want to leak your OpenGL textures & render buffer, on iOS4 you can simulate this by overloading didReceiveMemoryWarning and tracking your view's visibility).

    ORIGINAL, MORE BILIOUS ANSWER

    didReceiveMemoryWarning is absolutely useless.

    There's no guarantee that if you free up memory (even all of it) that you won't get killed.

    In my bitter experience it usually works like this on 2.x/3.0:

    1. mediaserverd leaks a bunch of memory

    2. my app gets killed

    Unfortunately, the reaper never thinks of killing mediaserverd.

    So if the memory usage isn't your fault, you've really only got two choices:

    1. ask the user to reboot (user assumes it's your fault, writes a scathing review)

    2. hope the culprit crashes (mediaserverd often obliges!)

    0 讨论(0)
  • 2020-12-05 12:38

    OK, several things to note:

    • didReceiveMemoryWarning will be called before an out-of-memory crash. Not other crashes. If you handle the warning properly and free up memory, then you can avoid the out-of-memory condition and not crash.
    • You can manually trigger a memory warning in the simulator under the Hardware menu. Highly recommend doing this to test your handling of didReceiveMemoryWarning.
    • Instruments helps you debug leaks (though not all of them) - it's not really that useful for crashes.
    • No, I don't personally use NSLog - I just breakpoint the memory warnings when I'm debugging.
    0 讨论(0)
提交回复
热议问题