Objective-C Literals with Data Abstract

Xcode 4.4 introduced Objective-C Literals which I think are great. Objective-C Literals are a collection of language enhancements that make it possible to do many common practices and patterns in Objective-C by writing less code. This includes boxing numbers, working with arrays and working with dictionaries. For instance, here’s some sample code for writing and reading an array without using Objective-C Literals:

[array setObject:@"one" atIndexedSubscript:0];
[array setObject:@"two" atIndexedSubscript:1];
[array setObject:@"three" atIndexedSubscript:2];

NSLog(@"%@", [array objectAtIndex:0]);
NSLog(@"%@", [array objectAtIndex:1]);
NSLog(@"%@", [array objectAtIndex:2]);

Here is the same code, now using the new enhancements for working with arrays:

array[0] = @"one";
array[1] = @"two";
array[2] = @"three";

NSLog(@"%@", array[0]);
NSLog(@"%@", array[1]);
NSLog(@"%@", array[2]);

Xcode even includes a refactoring called Convert to Modern Objective-C Syntax that will help you convert most of your code to this newer format.

Data Abstract, a multi-platform library for data access by RemObjects Software, also supports this new syntax when dealing with rows of data. The syntax was added to Data Abstract, according to Marc Hoffman, right after the Objective-C Literals support was announced at WWDC. Here is an example of working with a row of data before this change:

[row setValue:@"one" forKey:@"firstColumn"];
[row setValue:@"two" forKey:@"secondColumn"];
[row setValue:@"three" forKey:@"thirdColumn"];

NSLog(@"%@", [row valueForKey:@"firstColumn"]);
NSLog(@"%@", [row valueForKey:@"secondColumn"]);
NSLog(@"%@", [row valueForKey:@"thirdColumn"]);

And here is the newer syntax:

row[@"firstColumn"] = @"one";
row[@"secondColumn"] = @"two";
row[@"thirdColumn"] = @"three";

NSLog(@"%@", row[@"firstColumn"]);
NSLog(@"%@", row[@"secondColumn"]);
NSLog(@"%@", row[@"thirdColumn"]);

Fantastic I think! Easier to write, easy to read, and a very consistent and familiar way to access data by subscript. However, there is no built in refactoring in Xcode to change your old DADataTableRow code to this new format.

Stuck doing this by hand? I think not!

You can migrate your code to the newer syntax using Xcode’s Find & Replace. The Find & Replace in Xcode supports two powerful features we’ll use here: Regular Expresion (Regex) patterns and being able to preview and reject changes one-by-one.

To get started, load up your project in Xcode. On the left, select the Search Navigator (or press ⌘3). At the top of the Navigator, select Replace if Find is selected. Click the magnifying glass with the down arrow to the left of the search box and click Show Find Options. Under Style, select Regular Expression.


To replace the instances of code where values are being written, use the following search pattern:

[(.*) setValue:(.*) forKey:(.*)];

And use the following replace pattern:

1[3] = 2;

To replace the instances of code where row values are being read, use the following search pattern:

[(.*) valueForKey:(.*)]

And the following replace pattern:

1[2]

Click the Preview button to preview changes first. You can use the sliders in the middle of the preview window to accept and reject individual changes.


Once you’ve reviewed the changes, click Replace and you’re done! I’m happy any time I can use Regular Expressions without ending up with more problems than I started with.

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>