I see a lot of the following enum-to-string conversion in Objective-c/C at work. Stuff like:
static NSString *_TranslateMyAnimalToNSString(MyAnimal animal)
{
switch (animal) {
case MyAnimalDog:
return "my_animal_dog";
case MyAnimalCat:
return @"my_animal_cat";
case MyAnimalFish:
return @"my_animal_fish";
}
}
NS_ENUM(NSInteger, MyAnimal) {
MyAnimalDog,
MyAnimalCat,
MyAnimalFish,
};
Wouldn't it be faster and/or smaller to have a static dictionary? Something like:
static NSDictionary *animalsAndNames = @{@{MyAnimalCat} : @"my_animal_cat",
@{MyAnimalDog} : @"my_animal_dog",
@{MyAnimalFish} : @"my_animal_fish"};
The difference is small, but I'm trying to optimize the binary size and speed, which makes me inclined toward the latter.
Thanks for helping clarify.
The dictionary should be faster for a large amount of cases. A dictionary is a hashmap, which grants O(1)
lookup. A switch statement, on the other hand, will have to go through all entries thus requiring ϴ(n)
time.
Big-O notation is used to give an asymptotic upper bound to a particular function. That is, f(n) = O(g(n)) means that f(n) does not grow faster than g(n) as n goes to infinity (up to a constant). Similarly, big Ω denotes a lower bound. Therefore, the function f(n)=n+3 is both in Ω(1) and O(n^4), which is not very useful.
Big ϴ, then, denotes a strict bound. If f(n) = O(g(n)) and f(n) = Ω(g(n)) then also f(n) = ϴ(g(n)).
Often using big O suffices, as it makes no sense to advertise a linear algorithm as being in O(n^3), even though it is technically correct. In the case above however the emphasis is on the relative slowness of the switch case, which big O cannot correctly express, hence the usage of ϴ/Ω.
(However, I'm not sure sacrificing readability for correctness was the right choice.)