How to make a macro that takes a formatted string + several additional arguments, just like NSLog?

This is for practise. I try to build something similar to NSLog. Currently I have this:

#define LogThis(info) \
    [[MyLogger sharedLogger] logThis:info];\


- (void)logThis:(NSString*)info {
    fprintf(stderr, [[NSString stringWithFormat:@"  %@\n", info] cString]);
}

Currently all I can do is pass a simple @"string" to it, but no formats and arguments like I could with NSLog. The main advantage here is that I get rid of all this overhead which NSLog produces. For learning purpose I'd like to know how I can get multiple arguments to make something similar to NSLog, so that I could call:

LogThis(@"method foo received input value %d", inputValue)

Is this possible?

Upvotes: 1

Views: 215

Answers (2)

Nikolai Ruhe
Nikolai Ruhe

Reputation: 81868

Here’s how you define variadic macros in gcc’s cpp:

#define LogThis(format, ...) \
    do { printf(format, ## __VA_ARGS__); } while(0)

Upvotes: 3

Matt
Matt

Reputation: 678

There is a way, you define the last argument with a trailing '...'. To access the last arguments defined, prepend the argument name with ##. I have a similar Log macro that looks like:

#define LOGGER(format, args...)                                   \
    LogManager::log()->addEntry(format, ##args)

where the addEntry function takes in a printf-like format. An example call looks like

LOGGER("This is a debug string with %d arguments %s", 2, "hooray");

Upvotes: 0

Related Questions