2017-03-23 2 views
-2

클래스포스 목록 <Base> = 목록 <Derived> 및 법처럼 목록 <Derived>

public class Building 
{ 
    public string Name = "Not To Be Seen"; 
    ... 
} 

public class School: Building 
{ 
    public int NoOfRooms = 200; 
    public string Address = "123 Main St."; 
    ... 
} 

목표 (N 다른 클래스/사용 사례)

// This is a simple example, in reality this code is far more complex 
// the class "School" is private from the program 
List<Building> city = new List<School>(); 
// city will only have properties of the class School (or at least those are the only properties seen) 

Console.WriteLine(city[0].NoOfRooms.ToString()) // Outputs 200 
Console.WriteLine(city[0].Name) // Should not output anything 

이 올바르게에 따라 매우 수 있어야한다 보인다 목록을 변환합니다. 그러나, 나는 이것이 작동하도록하는 방법을 알아낼 수 없습니다. 그것은 그것이 공분산과 관련이있는 것처럼 보이지만, 이 아니라은 불변의 목록이나 유형을 원합니다. C#이 이런 종류의 변환을 쉽게 제공하지는 않습니다 (즉, 기본 클래스가 파생 클래스를 완전히 모방 할 수 있습니까?).

감사

+0

당신의 예제가 잘못되었습니다.'List Jill'은'ClassRoom' 속성을 가지고 있지 않습니다 ... –

+0

'public' 필드는 어떻게 파생 클래스에서 보이지 않을 것으로 예상합니까? –

+0

그리고 아니오, 당신은 사람이 선생님처럼 행동하도록 할 수 없으며, 사람 객체의 선생님에게만 속한 속성에 액세스 할 수 없습니다 ..... 나는 아마도 당신의 유산을 여기에서 재고 할 것입니다 ... 그리고 그것은 당신이 상속을 사용하지 마십시오 –

답변

0

업데이트 - 당신이 완전히 예를 변경하기 때문에, 나는 새로운 예를 반영하기 위해 내 대답을 업데이 트됩니다. 나는 이것을 한 번만하고있다. 그래서 누군가가 읽을 때, 내 대답이 질문과 일치하지 않는 것으로 보인다면 그것은 OP가 편집 중 불필요한 변경을하고 있기 때문입니다.


여기에 몇 가지 문제가 있습니다. List<Base> 변수가 List<Derived> 인스턴스를 참조 할 수 없습니다. 예를 들어 List<Base>Base 인스턴스를 List에 추가하는 작업을 구현해야하며 List<Derived>은 이러한 작업을 지원할 수 없기 때문입니다.

보다 일반적으로 참조 유형 (변수가 선언 된 유형)은 호출 코드에서 값을 사용할 수있는 인터페이스를 정의합니다. 따라서 예에서 city[0].NoOfRooms을 말할 수 있어야한다면 cityList<School>으로 선언되어야합니다. School은 여전히 ​​List<Building>에 저장 될 수 있지만 해당 목록에서 항목을 가져 오면 NoOfRooms 속성을 사용하기 전에 School으로 전송해야합니다. (이 작업을 수행하면 설계상의 오류가 있음을 알 수 있습니다.)

질문의 다른 부분은 Name 속성을 숨기는 것과 관련이 있습니다.

일부 언어에서는 "개인 상속"을 통해 이러한 효과를 얻을 수 있지만 C#에서는 그다지 중요하지 않습니다. 가장 가까운 것은 School이 아닌 Building에서 파생 된이 아니지만 (개인) Building 유형화 된 필드 또는 속성을 포함 할 수 있습니다. 그런 다음 에 School을 저장하는 것은 불가능합니다.

School은 아무 것도 반환하지 않는 게터로 Name 속성을 재정의하는 것이고 실제로 코드 주석이 제시 한 것과 더 가깝습니다. 질문에 대한 의견으로 당

0

에서 객체 당신의 List<Building>가 원래 School 객체 (또는 School에서 파생 된 클래스)로 구성하지 않는 한 임의로 School으로 캐스팅 할 수 없습니다. Hospital이라는 다른 클래스가 Building에서 파생되었고 자신의 속성이 NumberOfPatients이라고 말하면이 클래스는 해당 목록에있는 개체 중 하나였습니다.Hospital 인스턴스를 School에 캐스트 할 수없고 School에서만 사용할 수있는 속성을 호출 할 수 없습니다.이 작업은 의미가 없습니다. 당신은 여전히 ​​List<Building> 가게를 파생 된 것들 (당신이 Building, SchoolHospital 객체를 포함한 혼합 된 목록을 가지고 있도록)를 포함 Building 개체의 모든 종류를 가질 수 말했다

. 그런 다음 Linq OfType을 통해 특정 파생 유형의 객체를 열거 할 수 있습니다 (파일 상단에 using System.Linq; 추가). 따라서 buildingList.OfType<School>()과 같은 것이 있다면 School 개체 만 열거 할 수 있습니다.이 개체를 반복하고 School에서만 사용할 수있는 메서드/속성을 호출 할 수 있습니다.