Классы стиля Java-enum в Objective-C?
Я новичок в Obj-C, поэтому простите меня, если это глупый вопрос:
Как я могу реализовать некоторые в стиле Javas перечислений? Или, если быть более точным:
Мне нужен класс с некоторыми известными свойствами, которые являются фиксированными во время компиляции и уникальными для каждого экземпляра. Кроме того, мне нужен только один тип экземпляра.
Позвольте мне привести пример в Java:
public enum MessageTypes {
DEFAULT("white", "standard", 1),
EXPRESS("red", "expressMessage", 2),
BORADCAST("green", "broadcast", 3);
String color; String tagName; int dbId;
MessageTypes(String color, String tagName, int dbId) {
// you get the idea
}
//some methonds like getEnumByTagName
}
Как бы вы сделали что-то подобное в Objective-C? Я что-то упускаю? Это плохой шаблон?
Спасибо заранее!
ИЗМЕНИТЬ: Прошу прощения, если бы я не поняла. Я знаю, что obj-c перечисления не то, что я ищу (поскольку они только немного больше, чем typedef для int).
Я хотел бы создать набор экземпляров определенного типа (однотипных, неизменяемых). Одноэлементный шаблон в Apples Dev-Docs бесполезен, так как я хочу, чтобы несколько разных экземпляров класса каждый с отдельными значениями в своих свойствах.
Цель состоит в том, чтобы иметь несколько типов сообщений (около 20), которые могут быть назначены для Message как свойство. Каждый из моих типов сообщений имеет (фиксированный и предопределенный) цвет, значение атрибута (в XML-представлении) и числовой идентификатор.
В Java я бы использовал перечисление, как в моем примере кода. Но как создать различные MessageTypes и связать их с их свойствами в Obj-C?
Создание 20 подклассов MessageType (каждый из которых имеет одноэлементный экземпляр, содержащий свойства), похоже, очень много работает для такой простой задачи и полного переполнения.
Мой текущий подход заключается в создании класса с NSArray, в котором хранятся разные экземпляры. При первом доступе к методу, подобному +(id)messageTypeForId:NSInteger id_
, NSArray предварительно заполняется. Но это кажется совершенно неуклюжим и вовсе не элегантным...
Есть ли более удовлетворительный подход?
Ответы
Ответ 1
Существует не так много способов "более удовлетворительного подхода".
Обычным шаблоном Cocoa будет создание таких методов, как:
+ (MessageTypes*) sharedDefaultMessageType;
+ (MessageTypes*) sharedExpressMessageType;
+ (MessageTypes*) sharedBroadcastMessageType;
etc
а затем выполните их как:
+ (MessageTypes*) sharedDefaultMessageType
{
static MessageTypes* thisMessageType = nil;
if ( !thisMessageType ) {
thisMessageType = [[MessageTypes alloc] initWithColor:@"white" tagName:@"standard" dbId:1];
}
return thisMessageType;
}
В качестве альтернативы, сохранение общего типа MessageType * в NSMutableArray или NSMutableDictionary или предварительное вычисление их по мере того, как вы делаете, являются одинаково действительными approraches.
Обратите внимание, что вышеупомянутый метод "шаблон" может быть сгенерирован с помощью макроса, который можно записать в файле .m:
CREATEMESSAGETYPE( Default, @"white", @"standard", 1 )
CREATEMESSAGETYPE( Express, @"red", @"expressMessage", 2 )
CREATEMESSAGETYPE( Broadcast, @"green", @"broadcast", 3 )
который может быть "более удовлетворительным" или более уродливым, в зависимости от вашей точки зрения.
Ответ 2
Я думаю, что просто использую стандартный C-enum:
typedef enum { MT_WHITE, MT_RED, MT_GREEN } MessageType;
Затем вы просто используете его, как и любой другой тип данных:
@interface Blah {}
-(void) setMessageType:(MessageType)newMessageType;
@end
Ответ 3
Перечисления не являются объектами в C, и, следовательно, не в Objective-C. Это просто пользовательские скаляры, которые имеют ограниченный набор именованных значений, которые они могут принимать. Вы можете указать свойства объекта, которые являются перечисляемыми типами, которые, по моему мнению, ближе всего к тому, что вы ищете.
Если вам нужно что-то конкретное выполнить с помощью этой функции, вы можете отредактировать сообщение, чтобы указать, что это такое.
Ответ 4
У меня был тот же вопрос более или менее, но найти все вышеупомянутые решения неуклюже стилистически.
В частности, когда вы просто используете свойство C enum для объекта, вы теряете одноэлементную семантику перечислений Java. Самая большая свобода, которую я обнаружил при использовании перечислений Java, заключается в том, что экземпляры перечисления представляют собой одноэлементные подклассы и поэтому участвуют в полиморфизме методов. Еще более мощным, чем перечисления с уникальными атрибутами, являются перечисления с полиморфным поведением.
Учитывая, что это ключевая функция, с которой я столкнулся, кластер класса Objective-C с отдельными подклассами singleton - это подход с желаемым поведением, несмотря на то, что он немного отстает от стоимости и сложности реализации?