16

I've been asked to reduce the startup time of an iOS application. I am very familiar with the platform/tools in general but I haven't focussed upon application startup time before. I'm wondering if there are known patterns for attacking this problem?

I realize that I can simply measure the time it takes to go from main() through the completion of application:didFinishLaunchingWithOptions: (which includes any background loading tasks), but again, I am hoping there might be a more standardized way to do this.

Any suggestions would be greatly appreciated!

-M

Matty P
  • 881
  • 1
  • 7
  • 11

2 Answers2

15

from WWDC 2012 session 235

set the start point at the first line of code in main.m

#import <UIKit/UIKit.h>

CFAbsoluteTime StartTime;

int main(int argc, char *argv[])
{
    StartTime = CFAbsoluteTimeGetCurrent();

    @autoreleasepool {
        ...

set the end point somewhere in AppDelegate's application:didFinishLaunchingWithOptions:

extern CFAbsoluteTime StartTime;
 ...
dispatch_async(dispatch_get_main_queue(), ^{
    NSLog(@"Launched in %f sec", CFAbsoluteTimeGetCurrent() - StartTime);
});
Community
  • 1
  • 1
Gon
  • 1,135
  • 12
  • 22
  • Why would you `dispatch_async` that? It will through off the timing measurement since you queue on the next run loop. Probably not a big difference but seems like a completely unnecessary source of inaccuracy. – Jon Shier Jan 05 '15 at 18:41
  • 3
    @jshier `dispatch_async` is used so that the log prints when the user can actually interact with the app. The main queue is blocked in `application:didFinishLaunchingWithOptions`, and we want to know when the main thread is actually finished with all it's work. – bclymer Feb 13 '15 at 19:54
  • This is a little awkward, `application:didFinishLaunchingWithOptions` is on the main thread, so why do we need to dispatch on the main thread again? I think stopping the timer on first `viewDidAppear` might a bit more reasonable, but I haven't watch the session, might be missing something. – Zorayr Sep 08 '15 at 20:04
  • 1
    Even if `application:didFinishLaunchingWithOptions` finishes on the main thread there may be several other calls queued on the main thread which would be used in subsequent runloops. This makes sure these finish too which is good measure of when the user can use the app as their interaction will be at the back of this queue. – Neonkoala Oct 26 '15 at 23:48
1

Your method sounds like the correct one (I recommend using CFAbsoluteTime for your measurements).

One thing which may help you reduce the launch time is to avoid having View Controllers loaded from nibs on application launch. If I am not mistaken this forces them to be loaded into memory even before your app launches. Instead, alloc and init your view controllers dynamically when you need them. Note that you can still have the Views you'd like to be loaded by the view controllers stored in Nibs, you don't have to stop using IB. Just don't use IB to set static outlets for your app delegate.

Danra
  • 9,546
  • 5
  • 59
  • 117