Although NSlog is convenient for outputting messages to the console, I tire of the date/time and object information that it prints.
As an alternative, one can craft a macro that uses CFShow, which outputs Core Foundation objects to stderr. CFShow uses callbacks to objects to display their descriptions, which allows one to use “%@” like you would when calling NSLog.
I often include the following debug definition as part of my projects:
#define debug(format, ...) CFShow([NSString stringWithFormat:format, ## __VA_ARGS__]);
A few short examples follow showing the difference in output between NSLog and the debug macro shown above.
1
2
3
4
5
6
7
8
9
10
11
12
| struct point
{
int x;
int y;
};
typedef struct point POINT;
POINT topLeft;
topLeft.x = 15, topLeft.y = 20;
NSLog(@"x: %d y: %d", topLeft.x, topLeft.y);
debug(@"x: %d y: %d", topLeft.x, topLeft.y); |
The output will now look as follows:

Here’s another example, this time passing in an object:
1
2
3
4
5
6
7
8
9
10
| NSDate *today = [NSDate date];
NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
[dateFormat setDateFormat:@"EEEE MMMM d, YYYY"];
NSString *dateString = [dateFormat stringFromDate:today];
[dateFormat release];
...
NSLog(@"Date: %@", dateString);
debug(@"Date: %@", dateString); |
And the corresponding output:

Ahhh, much better.
Comments
4 Responses to “Yet Another Debug Output (NSLog Replacement)”
Leave Comment
All Content Copyright © 2008-2012 • iOS Developer Tips, All Rights Reserved.
Why not just use printf? You could do the following:
NSDate *today = [NSDate date];
NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
[dateFormat setDateFormat:@"EEEE MMMM d, YYYY"];
NSString *dateString = [dateFormat stringFromDate:today];
[dateFormat release];
…
NSLog(@”Date: %@”, dateString);
printf(“Date: %s”, [dateString cString]);
[Reply]
I agree, printf will work fine as you’ve shown, however, with printf you need to call the appropriate method to convert each object to its string representation or call the description method on the object. NSLog and/or CFShow will handle this process for you.
[Reply]
Thanks for the post.
I added #define NSLog(…) CFShow([NSString stringWithFormat:__VA_ARGS__])
to MyApp_Prefix.pch and it works beautifully.
[Reply]
It doesn’t work with ARC, I get the following:
error: Automatic Reference Counting Issue: Implicit conversion of an Objective-C pointer to ‘CFTypeRef’ (aka ‘const void *’) is disallowed with ARC
Any thoughts?
Regards,
Tim
[Reply]