4 Ways Precompiled Headers Cripple Your Code

crutches

Over-relying on precompiled headers can cripple your code!

[This post is part of the Code Smells in Objective-C series. Check out the rest here!]

Precompiled headers were invented for one purpose: to make compiling faster. Rather than parsing the same header files over and over, these files get parsed once, ahead of time. Speed is important! The faster you compile, the faster you can complete the feedback loop to see if recent changes were successful.

In Xcode, you do this by including the header files you want in a “prefix header,” and enabling “Precompile Prefix Header” so they get precompiled. But the idea behind a prefix header is different from precompiling. A prefix header is implicitly included at the start of every source file. For example, if your prefix header is Prefix.pch, it’s like each source file sneaks

#import "Prefix.pch"

at the top of the file, before anything else. This can be handy for project-wide #defines. (Just remember that in general, #defines are a code smell.)

It’s also handy for precompiled headers. The fact that every source file includes these precompiled headers is an artifact of being in the prefix header.

And this is where things start to go wrong…

Continue Reading…

Quality Coding Facebook Page

Facebook Like

Quality Coding now has a Facebook page!

I remember when blogs didn’t have comments. If you wanted to comment on someone’s post, you did so on your own blog. It worked surprisingly well. Community was created through “blogrolls” — lists of blogs in the sidebar.

Now all blogging systems have integrated comments. But because comments are tied to a particular blog post, it forces you to talk about what I write. And that’s not good enough. I want a place where you can initiate a topic, or share a thought, for everyone else in the Quality Coding community.

Continue Reading…

How to Debug iOS 5-Only Problems

Become a detective to debug iOS calls

For detective work, you need the right tools

Here’s the scenario: A bug is reported. But the bug occurs only on iOS 5. On earlier versions, everything’s a-okay.

Has this happened to you? I’ve dealt with it a couple of times. You can stare at the code as hard as you want, and come up with various theories. But you won’t get far that way. Why? Because on iOS 4, everything works. You won’t find any glaring errors.

So how do you debug iOS-specific problems? What you need is a diagnostic tool. Over on the iPhone Application Development blog, I describe a method that’s helped me crack tough problems. See iOS 5 Bug! How to Track It Down.

Photo by andercismo (license)

Welcome to This Blog’s New Home!

Welcome!

Welcome to the new home of Quality Coding — I’m glad you made it here!

I plopped down some money to buy a domain (qualitycoding.org), a hosting service (Dreamhost), and a WordPress theme (Standard Theme). You’ll experience a number of improvements, including:

  • Speed: Pages load quickly. And I mean super-fast!
  • Formatted code: My code fragments are now nicely formatted for easier reading.
  • Comment avatars: Just sign up at Gravatar, and your smiling face will make your comments more fun!
  • Comment threading: Now more than a single level of replies! The threads of conversation will be clearer.
  • Comment subscriptions: No more need to check back manually! Just click the checkbox when you add a comment, and you’ll be notified when anyone adds something new.
  • Easy sharing: Buttons float along the left side of each post. This makes it easy to share a post on Twitter, Facebook, Google+, etc.

I want you to get the most out of the new setup! Here are things you can do to maximize your experience:

Continue Reading…

How to Botch Your Objective-C Factory Method

Big [self alloc] factory

We all use factory methods, a.k.a. convenience methods. We often write them ourselves.

But there’s a wrong way, and a right way, to write a factory method for your Objective-C class. Do it wrong, and you cut off some features of Objective-C. Do it right, and you open yourself up to new object-oriented possibilities.

Let’s back up and review what we mean by a factory method. This is a convenience method that you invoke on a class to say, “Make me one of your kind.” (Some folks call this a “convenience constructor” which is odd to me, because the underlying mechanics are quite different from Java or C++.)

Factory method: The wrong way

Let’s say we have a simple class:

@interface Foo : NSObject
- (id)init;
@end

To create an autoreleased Foo object, we’d write

Foo *aFoo = [[[Foo alloc] init] autorelease];

But if you do this a lot, it becomes tedious and can clutter your code. So let’s create a factory method.

At this point, it’s tempting to copy and paste into the body of the new method:

+ (Foo *)foo
{
    return [[[Foo alloc] init] autorelease];
}

Looks fine. Everything works. So what’s the problem? Continue Reading…

Switching from Staging URL to Production URL

How to switch from staging URL to production URL?

How do you switch your app between a staging URL (for development and testing) and a production URL (for real world use)? I’ve changed my mind about my approach, because one size doesn’t fit all.

In 9 Code Smells of Preprocessor Use, I originally suggested that instead of using the preprocessor, it would be better to use a plist. Here’s the preprocessor code smell:

#if STAGING
static NSString *const fooServiceURL = @"https://dev.foo.com/services/fooservice";
#else
static NSString *const fooServiceURL = @"https://foo.com/services/fooservice";
#endif

I wrote, “Instead of defining these URLs in your code, treat them as resource definitions and place them in a plist, organized by type.” Continue Reading…

#imports Gone Wild! How to Tame File Dependencies

#imports (not Girls) Gone Wild

[This post is part of the Code Smells in Objective-C series. Check out the rest here!]

Like all C-based languages, Objective-C files usually come in pairs: there’s a header file, and an implementation file. Either can use the #import directive to include other header files. And if you’re not careful, it’s easy to create an explosion of file dependencies. What are the consequences? How do we tame #import dependencies?

File dependencies

Unnecessary #imports in a .m file are a nuisance. Why? Because it forces you to have those other files in your project. This isn’t a big deal when you’re working on a single project, but immediately causes trouble when you start a new project and want to reuse some source files.

But unnecessary #imports in a .h file are even worse: the problem grows exponentially! That’s because a header imports another header, which imports another header, and so on. Think of it as a dependency graph:

Dependency graph

Say A.h imports B.h and C.h. But B.h also imports D.h. So to add A to your project, you have to pull in B, C and D as well. And this graph is about as simple as it comes. If unnecessary #imports aren’t kept pruned away, the dependency graph will get out of hand. Continue Reading…

Video: Oh, the Methods You’ll Compose!

Dr. Seuss's book, "Oh, The Places You'll Go!"

In the spirit of Dr. Seuss, this video begins,

When a coder sits down to start banging out code,
the first thing to start crowding his cognitive load
is whether his program will do what it should.
“Correctness,” he says, “is what makes my code good.”

But it goes on to explain why clean, readable code matters, and ways to get there…

For such a short video, it has a lot of meat. And I love that last sentence!

But I see mixed reviews of the Kent Beck book that inspired it, Implementation Patterns. Have you read it? Please share your own short review in the comments below.

And if you haven’t read it… what did you think of the video?

Objective-C Is Still C (Not Java!)

Do you have your C book?

Do you have your K&R book?

October 2011 saw the passing of giants:

Simplicity. Power.

  • Steve Jobs. You work with his toys everyday.
  • Dennis Ritchie, inventor of the C programming language, co-inventor of Unix. You work with his stuff everyday (but we forget that).
  • John McCarthy, inventor of Lisp. We use the descendants of his invention every day (without realizing it).

By his vested Interweb powers, Tim O’Reilly has declared that October 30 be Dennis Ritchie Day. In his honor, I wanted to write something that’s been bothering me about the way people are learning Objective-C:

Objective-C is still C !

As a programmer, your most fundamental tools are the programming languages you use. If you don’t know the tool, you simply won’t be able to express things with both simplicity and power. And while I’m glad for the sudden interest in Objective-C, I’m troubled that so many people treat it like some kind of bastardized Java. They jump straight into messaging syntax and Foundation classes, while bypassing the powerhouse that’s available to them.

That powerhouse is the C language.

Continue Reading…

Simplify Your Tests with OCHamcrest “hasProperty”

hasProperty

OCHamcrest 1.6 is now available, featuring a great new matcher submitted by Justin Shacklette: hasProperty.

“hasProperty” is something of a misnomer, because it’s not just for properties. Any method, without arguments, that returns an object, is fair game. But I couldn’t think of a better name; I think it communicates well.

“hasProperty”: before

A little before-and-after may show you why I’m so excited about this matcher. Here’s a test I wrote before OCHamcrest 1.6:

- (void)testArrayFromURLStringArray
{
    // given
    NSArray *URLStrings = [NSArray arrayWithObjects:@"one", @"two", nil];

    // when
    NSMutableArray *downloads = [MyDownloader arrayFromURLStringArray:URLStrings];

    // then
    assertThat(downloads, hasCountOf(2));
    MyDownloader *download = [downloads objectAtIndex:0];
    assertThat([image URLString], is(@"one"));
    download = [downloads objectAtIndex:1];
    assertThat([image URLString], is(@"two"));
}

As you can see, the test creates an array of two strings. It passes this array to the method under test, a convenience method that creates an array of MyDownloader objects. The expectation is that the resulting array will have URLString values matching the original array of strings.

What I don’t like about this test is that the verification has to go through a number of steps: Continue Reading…

Page 1 of 212»