Defining an NSArray Constant in a Protocol

377 views Asked by At

I have a protocol class where I'm defining multiple String Constants and Array Constants containing these strings. I am porting over an android project.

In my Constants.h, I am declaring the NSString & NSArray constants as follows:

#imports.....

extern NSString *const constant1;
extern NSString *const constant2;

extern NSArray *const constantArr;

@protocol.....

Then in my Constants.m, I'm defining these constants:

#import "Constant.h"

NSString *const constant1 = @"Constant1";
NSString *const constant2 = @"Constant2";

//I get an error at this line
NSArray *const constantArr = [NSArray arrayWithObject: constant1, constant2, nil];

I get an error when defining the NSArray, it says Initializer element is not a compile-time constant. I believe I may be going about initialising the NSArray constant the wrong way.

Has anyone come across a similar issue or knows a way to initialise an NSArray Constant? Thanks

1

There are 1 answers

1
Cristik On BEST ANSWER

The problem is that you are trying to use runtime features at compile time, like instantiating an array (both [NSArray arrayWithObjects:] and the literal form @[] resolve to runtime allocations).

Constant strings don't suffer from this, as the compiler can allocate the bytes needed by the string in the data segment of the binary, however array's can't do this.

What you need is a piece of code that will execute when your application will be launched, and thus will be able to access runtime features.

The good news is that you can achieve this via the __attribute__((constructor)) modifier which tells the compiler to execute the decorated function when the binary is loaded, which coincidentally or not is when the app starts, before any AppDelegate code executes.

NSArray *constantAr;

//...

__attribute__((constructor))
static void initialize_constants() {
    constantArr = @[constant1, constant2];
}

The downside is that you will need to give up the const modifier, thus the array will no longer be a true constant.