Greg Heo

Blocks in Objective-C

Based on my "Introduction to Blocks" lightning talk.

I gave a quick introductory talk about blocks in Objective-C for iOS and Mac development tonight, and I thought I would put together some of the slides and my notes here as a post.

The least you need to know

Blocks are like closures. Or function pointers. Or lambdas. They’re available starting in OS X 10.6 Snow Leopard and iOS 4.

The symbol for blocks is this: ^ That’s a reasonable ASCII approximation of the real Greek lambda (upper case Λ, lower case λ).

Here’s a really simple block, the requisite “Hello world”:

^{ NSLog(@"Hello, world!"); };

Of course, that won’t actually do anything; it’s like declaring a function and not calling it. So here’s the revised version:

void (^myBlock)() = ^{
    NSLog(@"Hello, world!");
};
myBlock();

Block declarations look very much like function pointers, if you have dealt with those in C. In our example here:

Blocks for enumeration

Here’s our case study, a classic map (as in map/reduce): we have an array of a million objects. We need to iterate through the array and do some work for each array element.

We could use a for loop or NSEnumerator. In the more recent runtime, we might use fast enumeration like so:

NSArray *collection = [[NSArray alloc] ...];
for (id object in collection) {
    // do something here
}

Here’s the block way of doing it. We put the block code directly inline, although you can set up a block variable in advance if you like:

[myArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
    // do something
 }];

For the block function’s arguments:

Concurrency

Blocks are a natural gateway to Grand Central Dispatch (GCD) and being able to take advantage of parallelism, whether through multi-cores, multi-processors, or multi-threads. If it’s OK to iterate through the collection in parallel and out of order:

[myArray enumerateObjectsWithOptions:NSEnumerationConcurrent
  usingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
    // do something
 }];

So there’s nothing about blocks themselves that speeds up your code. What they offer is a very easy way to segment bits of hard-working code and then lean on GCD to handle the dispatching.

Further reading

There are a lot of topics such as block variables and memory management that are explained far better and in more detail than I could provide. Here are some links: