http://blog.csdn.net/wxr0323/article/details/7913950

Primitive Obsession(基本类型偏执)

偏执这个词实在是有点难懂。百度百科传送门

定义:Coding的时候总喜欢用基本类型,而不喜欢用对象。

影响:增加扩展和修改的复杂性。

来看两个函数。

Primitive:

  1. public void Method(string id, string name, string address)
  2. {
  3. //...
  4. }

Object:

  1. public void Method(object obj)
  2. {
  3. //obj.id.....
  4. //obj.name....
  5. //...
  6. }

随着需求日益变化,我们的参数会越来越多。那么使用基本类型的Method就会有很长的参数,演变成Long Parameter。Long Parameter会导致可读性差以及维护成本增加,直觉是这个方法职责太多。

Demo:媒婆、有Iphone4的小伙

小伙:

  1. class Boy
  2. {
  3. public string Name { get; set; }
  4. public string TelephoneNumber { get; set; }
  5. }

媒婆:

  1. class WomanMatchmaker
  2. {
  3. private readonly Boy boy;
  4. ...
  5. public string getBoyTelephoneNumberLastFourDigit()
  6. {
  7. const int digit = 4;
  8. var length = boy.TelephoneNumber.Length;
  9. return length > digit ? boy.TelephoneNumber.Substring(length - digit, length) : boy.TelephoneNumber;
  10. }
  11. }

媒婆需要小伙电话号码的后四位与姑娘电话号码后四位配对。配对成功后,问姑娘还有什么要求?

姑娘说只要用IPone4的小伙。无奈之下只好给小伙添加个属性。

  1. class Boy
  2. {
  3. public string Name { get; set; }
  4. public string TelephoneNumber { get; set; }
  5. public string TelePhoneType { get; set; }
  6. }

相应的还要给媒婆类添加一个方法:

  1. class WomanMatchmaker
  2. {
  3. private readonly Boy boy;
  4. public WomanMatchmaker(Boy boy)
  5. {
  6. this.boy = boy;
  7. }
  8. public string GetBoyTelephoneNumberLastFourDigit()
  9. {
  10. const int digit = 4;
  11. var length = boy.TelephoneNumber.Length;
  12. return length > digit ? boy.TelephoneNumber.Substring(length - digit, length) : boy.TelephoneNumber;
  13. }
  14. public string GetBoyTelephoneType()
  15. {
  16. return boy.TelePhoneType;
  17. }
  18. }

到此为止。如果姑娘还要问手机用的什么操作系统,那还要加属性加方法?另外这段代码有个很明显的BadSmell:Feature Envy。

重构:将基本类型替换为Object。 将所有关于手机的信息放在一起。

Extract Phone Class:

  1. class Phone
  2. {
  3. private const int DIGIT = 4;
  4. public string Number { get; set; }
  5. public string Category { get; set; }
  6. public string GetLastFourDigit()
  7. {
  8. var length = Number.Length;
  9. return length > DIGIT ? Number.Substring(length - DIGIT, length) : Number;
  10. }
  11. public string GetCategory()
  12. {
  13. return BuildCategory(Category);
  14. }
  15. }

小伙带个手机就行了:

  1. class Boy
  2. {
  3. public string Name { get; set; }
  4. public Phone phone { get; set; }
  5. }

媒婆也轻松了:

  1. class WomanMatchmaker
  2. {
  3. private readonly Boy boy;
  4. public R_WomanMatchmaker(Boy boy)
  5. {
  6. this.boy = boy;
  7. }
  8. public string getBoyTelephoneNumberLastFourDigit()
  9. {
  10. return boy.phone.GetLastFourDigit();
  11. }
  12. public string GetBoyTelephoneCategory()
  13. {
  14. return boy.phone.GetCategory();
  15. }
  16. }

姑娘问手机是哪个地方产的? 我们就在Phone中添加一属性,媒婆类里加一委托即可。

05-08 15:42