C #에서 클래스는 다른 클래스와 인터페이스에서 상속 할 수 있습니까?


130

클래스와 인터페이스에서 클래스를 상속받을 수 있는지 알고 싶습니다. 아래 예제 코드는 작동하지 않지만 원하는 작업을 전달한다고 생각합니다. 내가하고 싶은 이유는 회사에서 USB, 직렬, 이더넷 등의 장치를 만들기 때문입니다. 모든 응용 프로그램에서 공통 사항 (연결, 연결 해제, 펌웨어 가져 오기 등)을 동일하게 유지하는 데 도움이되는 모든 장치에 대한 프로그램을 작성하는 데 사용할 수있는 일반 구성 요소 / 인터페이스를 개발하려고합니다.

이 질문에 추가하려면 GenericDevice가 다른 프로젝트에있는 경우 해당 프로젝트에 IOurDevices 인터페이스를 넣은 다음 첫 번째 프로젝트에 대한 참조를 추가하면 USBDevice 클래스가 인터페이스를 구현하도록 할 수 있습니까? 하나의 프로젝트를 참조하고 장치가 무엇인지에 따라 다른 인터페이스를 구현하고 싶습니다.

class GenericDevice
{
   private string _connectionState;
   public connectionState
   {
      get{return _connectionState; }
      set{ _connectionState = value;}
   }
}

interface IOurDevices
{
   void connectToDevice();
   void DisconnectDevice();
   void GetFirmwareVersion();
}

class USBDevice : IOurDevices : GenericDevice
{
   //here I would define the methods in the interface
   //like this...
   void connectToDevice()
   {
       connectionState = "connected";
   }
}

//so that in my main program I can do this...

class myProgram
{
   main()
   {
      USBDevice myUSB = new USBDevice();
      myUSB.ConnectToDevice;
   }
}

5
나중에 참조 할 수 있도록 C # 사양의 섹션 10.1.4에서는 여러 기본 유형이있는 클래스를 선언하는 방법을 정확하게 설명합니다.
Eric Lippert

@Eric Lippert :이 사례가 올바른 방식이며 향후에 제공 될 수 있는지에 대해 이해하도록 도와 주실 수 있습니까?
Gul Md Ershad

답변:


246

예. 시험:

class USBDevice : GenericDevice, IOurDevice

노트 : 기본 클래스는 인터페이스 이름 목록 앞에 와야합니다.

물론, 인터페이스가 정의한 모든 멤버를 구현해야합니다. 그러나 기본 클래스에 인터페이스 멤버와 일치하는 멤버가 포함 된 경우 기본 클래스 멤버는 인터페이스 멤버의 구현으로 작동 할 수 있으며 수동으로 다시 구현하지 않아도됩니다.


1
그렇습니다. 왜 그렇게 생각하지 않았어요! 그리고 아래 의견에. (클래스는 인터페이스를 상속하지 않고 IMPLEMENT 인터페이스를 상속받습니다)
PICyourBrain

1
@Jordan은 또한 기본 클래스와 상속되는 인터페이스 목록이 초기 콜론 (@Mehrdad의 예) 뒤에 쉼표로 구분됩니다.
JMD

1
기본 클래스가 인터페이스를 구현하면 파생 클래스가 자동으로 해당 인터페이스를 구현합니다 USBDevice : IOurDevice. 구현을 명시 적으로 추가해도 기본 클래스에는 영향을 미치지 않지만 인터페이스에 중점을 두는 데 도움이 될 수 있습니다.
STW

1
@David, 틀린 것은 아니지만 @Jordan의 코드가 작동하지 못하게하는 용어는 아닙니다. 잘못된 구문입니다.
JMD

2
또한베이스와 인터페이스 모두에서 동일한 멤버에 관해 묻고 싶은 질문을 해결하기 위해 +1.
Riegardt Steyn

21

아뇨 그러나 클래스에서 상속 하고 하나 이상의 인터페이스를 구현할 수 있습니다.

이와 같은 개념을 논의 할 때는 명확한 용어가 중요합니다. 여기서 볼 수있는 것 중 하나는 여기와 인쇄본에서 Jon Skeet의 글을 표시하는 것입니다.


8
또는 Eric Lippert는 글이 매우 정확합니다.
Mathias

21

질문과 관련이 없으며 (Mehrdad의 답변으로 이동해야 함) 나는 이것이 nitpicky로 간주되지 않기를 바랍니다 : 클래스는 인터페이스를 상속 하지 않습니다. 구현 합니다.

.NET은 다중 상속을 지원하지 않으므로 용어를 올바르게 유지하면 통신에 도움이 될 수 있습니다. 클래스는 하나의 수퍼 클래스에서 상속 할 수 있으며 원하는 수의 인터페이스를 구현할 수 있습니다.


Eric의 의견에 대한 응답으로 인터페이스 "상속", "구현", "필수"또는 "반입"여부에 대한 다른 개발자와의 토론이있었습니다.

public interface ITwo : IOne

기술적 인 대답은 몇 가지 이유로 ITwo상속 IOne됩니다.

  • 인터페이스는 결코 그래서 주장, 구현이 없습니다 ITwo 구현을 IOne 이 잘못되었다고
  • ITwo상속 IOne하는 경우 방법은 MethodOne()에있는 IOne다음도에서 accesible입니다 ITwo. 즉 : ((ITwo)someObject).MethodOne())ITwo대한 정의를 명시 적으로 포함하지 않더라도 유효 합니다.MethodOne()
  • ... 런타임이 그렇게 말했기 때문에! typeof(IOne).IsAssignableFrom(typeof(ITwo))보고true

우리는 마침내 인터페이스가 진정한 / 전체 상속을 지원한다는 데 동의했습니다. 누락 된 상속 기능 (예 : 재정의, 추상 / 가상 접근 자 등)이 인터페이스 상속이 아닌 인터페이스에서 누락되었습니다. 여전히 개념을 단순하거나 명확하게 만들지는 않지만 Eric의 세계에서 실제로 일어나는 일을 이해하는 데 도움이됩니다. :-)


3
불행히도 인터페이스는 다른 인터페이스를 상속 합니다. 나는 그 단어의 선택이 불행하다는 것을 알지만, 우리는 지금 그것에 붙어 있습니다. 인터페이스는 다른 인터페이스가 필요한 것으로 생각 합니다. 즉, "인터페이스 IFoo : IBar"라고 말하면 "IFoo의 구현자는 IBar도 구현해야합니다"를 의미합니다.
Eric Lippert

@Eric 나는 그것이 불분명 한 용어이며 동의를 한참 전에 동료와 토론했다. 결국 우리는 "ITwo는 IOne을 물려받습니다"라고 말하기로 결정했습니다. 몇 가지 작은 이유로 답변을 업데이트 할 것입니다 (댓글에 명확하게 맞지 않기 때문입니다).
STW

확실한; "A가 B에서 상 속됨"을 "B의 구성원이 모두 A의 구성원 임"을 의미하는 것으로 정의하면 인터페이스는 기본 인터페이스에서 "상속"합니다. 이것은 합리적인 정의입니다. 그러나 "상속"은 추상적이고 구현되지 않은 멤버를 공유하는 것이 아니라 구현을 상속 하는 것보다 더 엄격하다고 생각 합니다 . 인터페이스에는 구현이 없으므로 인터페이스를 다른 것으로 상속하는 것으로 생각하는 것이 다소 불쾌합니다. 미묘하고 논란의 여지가있는 지점입니다.
Eric Lippert

내가 좋아하는 또 다른 용어는 "확장"입니다. 따라서 "인터페이스 IFoo : IBar"를 읽으면 IFoo가 IBar의 요구 사항을 확장한다는 의미입니다.
Jasonh

1
@Joan : 클래스가 인터페이스를 구현하고 상속 할 수없는 것이 맞습니다 . Eric이 지적한 요점은 인터페이스 가 다른 인터페이스를 상속 할 수 있다는 것입니다. 인터페이스가 구현이 아닌 "사양"이기 때문에 요약하기가 다소 어려울 수 있습니다.
STW

1

내 질문의 두 번째 부분에 대한 답을 찾았습니다. 예, 클래스가 인터페이스가 public으로 선언되어있는 한 다른 클래스에있는 인터페이스를 구현할 수 있습니다.


모든 경우에 공개 될 필요는 없습니다. 접근성이 뛰어납니다. 예를 들어 class ContainsAll { private interface INested { /* ... */ } private class MyExample : INested { /* ... */ } }, MyExample클래스는 중첩 된 개인 인터페이스를 구현합니다. 다른 예에서 중첩 된 인터페이스 (및 포함하는 클래스)는입니다 internal. 그것은 모두 누가 그들을 사용해야하고 귀찮게 해야하는지에 달려 있습니다.
Jeppe Stig Nielsen
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.