2016-09-10 6 views
0

저는 통신 프로젝트를 진행 중입니다. 내 프로젝트에서 Open/Closed 원칙을 구현했습니다. 아래는 수업입니다. 나는 비디오 서비스를 구현해야하는 경우OOPS 열기/닫기 원칙

MainServiceClass.CS

public abstract class BaseServiceClass 
{ 
    public abstract IEnumerable<string> GetServiceData(); 
    public abstract IEnumerable<string> GetDashBoardData(); 
} 

Web_Service.CS

public class WebServiceClass : BaseServiceClass 
{ 
    public override IEnumerable<string> GetServiceData() 
    { 
     List<string> MyList = new List<string>(); 
     return MyList; 
    } 

    public override IEnumerable<string> GetDashBoardData() 
    { 
     List<string> MyList = new List<string>(); 
     return MyList; 
    } 
} 

Voice_Service.CS

향후
public class VoiceSericeClass : BaseServiceClass 
{ 
    public override IEnumerable<string> GetServiceData() 
    { 
     List<string> MyList = new List<string>(); 
     return MyList; 
    } 

    public override IEnumerable<string> GetDashBoardData() 
    { 
     List<string> MyList = new List<string>(); 
     return MyList; 
    } 
} 

, 나는이 만들어집니다 새로운 Video_Service 클래스. 나는 Open/Close 원칙을 달성 할 것이라고 믿습니다.

MainServiceClass.cs에 새 메서드를 추가해야하는 경우 새 메서드 (GetNewTypeOfData())를 추가합니다.

질문 : 여기서 수업을 수정하고 있습니다. 그래도 OCP를 따르고 있습니까? 또는 MainServiceClass.cs에 새 메서드를 추가하는 방법이 있습니까 ??

좋습니다.

P. 나는 모든 파생 클래스 즉 Web_Service.cs, Voice_Service.cs이 메소드를 구현해야하고, CrudaLilium 응답 후 내 질문에 업데이트 Video_Service.cs

.

이것은 제 이해입니다. 내가 틀렸다면 나를 바로 잡아주세요.

내 현재 코드 :

public interface IMainBase 
{ 
    IEnumerable<string> GetData2016(); 
} 

public class VoiceService : IMainBase 
{ 
    public IEnumerable<string> GetData2016() 
    { 
     return Enumerable.Empty<string>(); 
    } 
} 

내가 그래서 내가 다시 2018의 새로운 요구 사항을 얻을 것 2017

public interface IMainBase 
{ 
    IEnumerable<string> GetData2016(); 
}  

public class VoiceService : IMainBase 
{ 
    public IEnumerable<string> GetData2016() 
    { 
     return Enumerable.Empty<string>(); 
    } 
} 

//New Code will be Added in 2017....Start 

public interface IMainBase2017 : IMainBase 
{ 
    IEnumerable<string> GetData2017(); 
} 

public class voiceService2017 : VoiceService, IMainBase2017 
{ 
    public IEnumerable<string> GetData2017() 
    { 
     return Enumerable.Empty<string>(); 
    } 
} 

//New Code Added be in 2017...Ended 

내 코드를 업데이트 할 2017 년에 새로운 요구 사항을 얻을 것입니다. 위의 코드 당, 내가 OCP를 위반하고 있지 않다 그래서, 나는 2018

public interface IMainBase 
{ 
    IEnumerable<string> GetData2016(); 
}  

public class VoiceService : IMainBase 
{ 
    public IEnumerable<string> GetData2016() 
    { 
     return Enumerable.Empty<string>(); 
    } 
} 

//New Code will be Added in 2017....Start 

public interface IMainBase2017 : IMainBase 
{ 
    IEnumerable<string> GetData2017(); 
} 

public class voiceService2017 : VoiceService, IMainBase2017 
{ 
    public IEnumerable<string> GetData2017() 
    { 
     return Enumerable.Empty<string>(); 
    } 
} 

//New Code Added be in 2017...Ended 

//New Code will be Added in 2018...Start 

public class WebService2018 : IMainBase2017 
{ 
    public IEnumerable<string> GetData2016() 
    { 
     return Enumerable.Empty<string>(); 
    } 

    public IEnumerable<string> GetData2017() 
    { 
     return Enumerable.Empty<string>(); 
    } 
} 


//New Code will be Added in 2018...End 

에 내 코드를 업데이트합니다. 이것은 좋은 습관입니까 아니면 대안적인 방법이 있습니까?

+0

당신은 모든 클래스에 나타날 새로운 방법과 구현을 추가하고 싶다고 말하고 있습니까? – Turbot

+0

예, MainService 클래스에 새 메서드를 추가하고 나중에 파생 클래스에서 재정의합니다. – KiddoDeveloper

+0

새 기능을 추가 할 때 기존 클래스를 변경해야하는 경우 OCP를 위반하게됩니다. 따라서 OCP를 따르지 않습니다. 너는 그것을 깨뜨리고있다. – Steven

답변

1

Video_Service 만들기는 문제가되지 않지만 BaseServiceClass을 변경하면 원칙을 따르지 않게됩니다.

추상화하면 BaseServiceClass을 상속 한 다른 모든 클래스를 수정해야합니다. 그러나 당신이 추상적으로 만들지 않더라도, 여러분의 BaseServiceClass을 사용하는 모든 현재 클라이언트 클래스는 이미 가지고있는 2를 제외하고는 다른 어떤 메소드도 사용하지 않기 때문에 무의미한 것처럼 보입니다.

클라이언트 클래스가 세 번째 방법을 사용해야하는 경우 BaseServiceClass에서 상속받을 다른 추상 클래스 (예 : BaseServiceClass2)를 만들고 거기에 새 메서드를 추가하고 클라이언트를이 클래스에 종속시키는 것이 좋습니다. 여기에서 기존 클래스를 확장하기 위해 WebServiceClass, VoiceSericeClass을 새로 작성하고 BaseServiceClass2에서 상속 받고 어댑터 패턴을 사용하십시오.

예제 코드 : 당신이 BaseServiceClass 인터페이스를 만들 경우

public abstract class BaseServiceClass 
    { 
     public abstract IEnumerable<string> GetServiceData(); 
     public abstract IEnumerable<string> GetDashBoardData(); 
    } 

    public abstract class BaseServiceClass2 : BaseServiceClass 
    { 
     public abstract IEnumerable<string> GetNewTypeOfData(); 
    } 


    public class WebServiceClass2 : BaseServiceClass2 
    { 
     private BaseServiceClass adaptee; 

     WebServiceClass2(BaseServiceClass adaptee) 
     { 
      this.adaptee = adaptee; 
     } 

     public override IEnumerable<string> GetDashBoardData() 
     { 
      return adaptee.GetDashBoardData(); 
     } 

     public override IEnumerable<string> GetNewTypeOfData() 
     { 
      return Enumerable.Empty<string>(); 
     } 

     public override IEnumerable<string> GetServiceData() 
     { 
      return adaptee.GetServiceData(); 
     } 
    } 

그것은 훨씬 더 좋을 것이다 당신은 새로운 것을 추가해야 할 경우 당신은 단지 그것에서 내재 새로운 인터페이스를 creat에와 같이 앞의 예에서, 만들 것입니다 당신의 클라이언트 클래스는 새 인터페이스에 따라 다르므로 WebServiceClass, VoiceSericeClass 등을 상속받은 새 클래스를 만들고 새 인터페이스를 구현할 수 있습니다.

예 :

public interface IBaseServiceClass 
    { 
     IEnumerable<string> GetServiceData(); 
     IEnumerable<string> GetDashBoardData(); 
    } 

    public interface IBaseServiceClass2 : IBaseServiceClass 
    { 
     IEnumerable<string> GetNewTypeOfData(); 
    } 


    public class WebServiceClass2 : WebServiceClass, IBaseServiceClass2 
    { 
     public IEnumerable<string> GetNewTypeOfData() 
     { 
      return Enumerable.Empty<string>(); 
     } 
    } 

    public class WebServiceClass : IBaseServiceClass 
    { 
     public IEnumerable<string> GetServiceData() 
     { 
      List<string> MyList = new List<string>(); 
      return MyList; 
     } 

     public IEnumerable<string> GetDashBoardData() 
     { 
      List<string> MyList = new List<string>(); 
      return MyList; 
     } 
    } 

클래스/인터페이스 이름은 자리 표시 자로 사용되며, 더 나은 더 의미있는 방식으로 이름을 것입니다.

+0

답장을 보내 주셔서 감사합니다. 나는 질문이있다. 질문 : 현재 프로덕션 서버에 프로젝트를 배포했습니다. 내년에는 요구 사항이 생성되므로 MainService 클래스에 새 메서드를 구현해야합니다. 따라서, OCP를 위반해서는 안되며 귀하의 제안에 따라 새로운 인터페이스/클래스를 추가해야합니다. 좋아, 나는 그것을 추가 할 것이다. 나는 어떤 간격 후에 새로운 방법에 대한 요청을받을 수 있습니다. 그렇다면 각 요청마다 새로운 추상/인터페이스를 생성해야합니까? – KiddoDeveloper

+0

내가 내 질문을 설명 할 수없는 경우 알려주십시오. 더 자세히 설명 드리겠습니다. – KiddoDeveloper

+0

예. 새 인터페이스를 만들고 기존 클래스를 확장하지만 신 클래스를 만들지 않아야합니다. – CrudaLilium