2017-02-25 76 views
0

我有一個基於枚舉值構建對象的類。所以這些對象的幾個屬性基於一些枚舉值,一個類型。基於枚舉構造對象

選項1:

typedef NS_ENUM (NSUInteger, ViewType) { 
    VTHouse, 
    VTCar, 
    VTChair, 
    ... 
}; 

我有幾種方法,確定基於該類型的對象的屬性。

- (NSURL*)urlForViewType:(ViewType)type { 

    NSURL *url = nil; 

    switch (type) { 
     case VTHouse: { 
      url = [NSURL URLWithString:@"House url"]; 
      break; 
     } 
     case VTCar: { 
      url = [NSURL URLWithString:@"Car url"]; 
      break; 
     } 
     case VTChair: { 
      url = [NSURL URLWithString:@"Chair url"]; 
      break; 
     } 
     ... 
    } 

    return url; 
} 

- (NSURL*)isSelectableViewType:(ViewType)type { 

    BOOL selectable = NO; 

    switch (type) { 
     case VTHouse: { 
      selectable = YES; 
      break; 
     } 
     case VTCar: { 
      selectable = YES; 
      break; 
     } 
     default: { 
      break; 
     } 
    } 

    return selectable; 
} 

- (NSURL*)colorForViewType:(ViewType)type { 

    UIColor *color = nil; 

    switch (type) { 
     case VTHouse: { 
      color = [UIColor redColor]; 
      break; 
     } 
     case VTCar: { 
      color = [UIColor blueColor]; 
      break; 
     } 
     case VTChair: { 
      color = [UIColor lightGrayColor]; 
      break; 
     } 
     ... 
    } 

    return color; 
} 

// And so on... 

然後我有一個這個類的用戶會調用的方法。

- (SpecialView*)specialViewForType:(ViewType)type { 

    NSURL *url = [self urlForViewType:type]; 
    BOOL selectable = [self isSelectableViewType:type]; 
    UIColor *color = [self colorForViewType:type]; 
    ... 

    return [SpecialView specialViewURL:url selectable:selectable color:color ...]; 
} 

這一切都很好,但它給我一個不安的感覺。有些事情感覺不對。也許這是所有的開關。我覺得有一個更乾淨的方法來做到這一點。

擺脫大部分開關的另一種選擇是類似的;

選項2:

- (SpecialView*)specialViewForType:(ViewType)type { 

    SpecialView *view = nil; 

    switch (type) { 
     case VTHouse: { 
      view = [self specialViewHouse]; 
      break; 
     } 
     case VTCar: { 
      view = [self specialViewCar]; 
      break; 
     } 
     case VTChair: { 
      view = [self specialViewChair]; 
      break; 
     } 
     ... 
    } 
    return view; 
} 

其中每種方法已經知道哪些屬性爲每個類型設置。但我更喜歡選項1.

所以我的問題是;有沒有人對如何改進這種代碼有任何建議?

+0

你可以用字典替換開關盒,並做更簡單的查找。某些產生相同結果的開關盒規則也可以分組。此外,如果您有視圖的通用協議,則可以在每個子類中實現顏色/可選邏輯以避免切換。 – Andy

回答

0

開關是最後一個千年的亞類。最簡單的方法是擁有(私人)子類。從該子類創建實例。

@implementation BaseClass 
+ (instancetype)newBaseClassForType:(ViewType)viewType 
{ 
    // Do a look-up to a array or a one-time switch to get the subclass 
    Class appropiateSubclass = …; 
    return [appropiateSubclass new]; 
} 

然後,子類可以覆蓋方法,即。 e .:

@implementation HouswSubClass 
- (BOOL)isSelectable { return YES; } // BTW: The return type was wrong 

更重要的是:爲什麼你有一個枚舉?

+0

我喜歡並且不喜歡子類的想法。我有大約15種不同類型,未來可能會更多。所以有一個子類只是爲了具有某些預定的屬性,似乎它可能是矯枉過正的,雖然組織良好。我使用枚舉來簡化視圖控制器的接口。所以它必須知道的是它想要的是什麼類型的視圖。什麼比這裏的枚舉更好? – OleShoebill

+0

存儲類,而不是自制類型。請記住,這些類是Objective-C中的對象。但是,有15個小類沒有什麼不對。他們可能是私人的。 –