Я часто использую : tabo , чтобы закрыть все остальные вкладки.
Прелюдия: Полезно понимать разницу между директивами прекомпилятора и истинными константами. #define
просто выполняет замену текста до того, как компилятор построит код. Это отлично подходит для числовых констант и определений типов, но не всегда является лучшей идеей для вызовов функций или методов. Я исхожу из предположения, что вам действительно нужна настоящая константа, а это означает, что код для создания пути поиска должен выполняться только один раз.
В вашем файле MyClass.m определите переменную и заполните его методом + initialize
следующим образом:
static NSArray *documentsDir;
@implementation MyClass
+ (void) initialize {
if (documentsDir == nil) {
documentsDir = [[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory , NSUserDomainMask, YES) lastObject] retain];
}
}
...
@end
Модификатор static
делает его видимым только в той единице компиляции, где он объявлен. Для простой константы это все, что вам нужно.
Если у класса есть подклассы, + initialize
будет вызываться один раз для каждого подкласса (по умолчанию), поэтому вам нужно проверить, равен ли documentsDir
nil
, прежде чем назначать ему, чтобы вы не допускайте утечки памяти. (Или, как указывает Питер Льюис, вы можете проверить, является ли инициализируемый в настоящее время класс MyClass, используя метод ==
или -isMemberOfClass:
.) Если подклассы также необходим прямой доступ к константе, вам нужно будет предварительно объявить переменную как extern
в файле MyClass.h (который включают дочерние классы):
extern NSArray *documentsDir;
@interface MyClass : NSObject
...
@end
Если вы предварительно -объявление переменной как extern, вы должны удалить ключевое слово static
из определения, чтобы избежать ошибок компиляции. Это необходимо, чтобы переменная могла охватывать несколько единиц компиляции. (Ах, радости C ...)
Примечание: В коде Objective-C лучший способ объявить что-то как extern
- использовать OBJC_EXPORT
(a #define
объявлен в
), который устанавливается в зависимости от того, используете ли вы C ++. Просто замените extern
на OBJC_EXPORT
, и все готово.
Изменить: Я только что наткнулся на вопрос SO .
Самое простое решение - просто изменить пути, чтобы они были статической переменной, и вычислить ее только один раз, например:
+(NSString *) getDocumentsDir {
static NSString *documentsDir = nil;
if ( !documentsDir ) {
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory , NSUserDomainMask, YES);
documentsDir = [paths objectAtIndex: 0];
}
return documentsDir;
}
«static» сообщает компилятору, что documentsDir фактически является глобальной переменной, хотя доступен только внутри функции. Таким образом, он инициализируется значением nil, и первый вызов getDocumentsDir оценивает его, а затем последующие вызовы возвращают предварительно оцененное значение.