2012-04-29 2 views
1
public void GetProps(Parent p){ 

    // want to access lots of child properties here 
    string childProp1 = p.prop1; 
    bool childProp2 = p.prop2; 
    bool childProp3 = p.prop3; 

} 

Однако компилятор жалуется, чтоC#, доступ к свойствам дочернего объекта из родительской ссылки?

"Родитель не содержит определения prop1"

функция будет принимать в различных подтипов класса Parent.

Все подклассы имеют этот

public override string prop1 { get; set; } 

Есть ли способ достичь этого?

EDIT: Для того, чтобы вопрос яснее

я тока имеют гигантский если-ELSEIF, где я сделать что-то вроде

if(p is Child0){ 
     Child0 ch = p as Child0; 

     // want to access lots of child properties here 
     string childProp1 = ch.prop1; 
     bool childProp2 = ch.prop2; 
     bool childProp3 = ch.prop3; 

}else if(p is Child1){ 
     Child1 ch = p as Child1; 

     // want to access lots of child properties here 
     string childProp1 = ch.prop1; 
     bool childProp2 = ch.prop2; 
     bool childProp3 = ch.prop3; 

}else if(...// and many more 

Теперь я хотел, чтобы удалить все избыточный код и сделать один функцию, которая может справиться со всем этим.

+0

Я ответил, насколько я могу дать отрывочную информацию - если бы вы могли дать больше контекста о том, чего вы пытаетесь достичь, это действительно поможет. –

+1

Как вы используете ключевое слово ref как параметр переменной? –

+0

@DarrenDavies отредактировал вопрос –

ответ

4

Если все дочерние классы должны иметь свойства (но с различными реализациями), вы должны объявить их как абстрактные свойства в базовом классе (Parent), а затем реализовывать их в дочерних классах.

Если некоторые производные классы не будут иметь эти свойства, то что вы ожидаете от текущего GetProps?

EDIT: Если вы используете C# 4, и вы определенно не можете получить лучший дизайн класса (где родительский класс объявляет свойство), вы можете использовать динамическую типизацию:

public void GetProps(Parent p) { 
    dynamic d = p; 
    string childProp1 = d.prop1; 
    bool childProp2 = d.prop2; 
    bool childProp3 = d.prop3; 
    // ...  
} 

Я d рассматривают это как последнее средство, хотя ...

+0

извините, Джон, я не хороший писатель, но я добавил больше подробностей к моему вопросу. Также я получаю доступ к этому на внешней dll, и у меня нет доступа к источнику. –

+0

@KevinBoyd: Я сомневаюсь, что подклассы имеют 'override', если свойство фактически не находится в базовом классе ... Если бы вы могли дать короткий, но * полный * пример, это действительно помогло бы. –

+0

Джон, линия наследования довольно длинная. И я использую ссылку родителя верхнего уровня, например Parent ---> SubP10 ----> SubP9 ---> SubP8 ...-----> Ребенок. Любой из родителей может иметь определение prop1. –

0

Если свойство определено в промежуточном классе между родителем и дочерним элементом, и вы не имеете ссылки на этот промежуточный класс во время разработки, тогда вы можете использовать отражение для получения недвижимость. Но похоже, что вы должны использовать наиболее подходящий дочерний родительский элемент вместо простого родителя.

+0

Приятная идея! Пример поможет! Отражение и динамика, как кажется Jon, похоже, являются существующими опциями. –

1

Как я понял из вашего вопроса, вы хотите получить доступ к членам Детского класса из объекта родительского класса.

Это поведение не допускается в ООП. Один из способов может быть предложен Джоном Скитом для создания абстрактного базового класса и реализации необходимых членов в классах детей.

Другим способом round может быть присвоение требуемых значений членам базового класса в конструкторе производного класса с использованием базовой конструкции. Я не знаю, что это решит вашу проблему или нет.Но Рассмотрим следующий фрагмент кода, например:

public class BaseClass 
{ 
    public string FirstName = "Base Class"; 
    public string LastName = "Base Class"; 
} 

public class DerivedClass : BaseClass 
{ 
    public DerivedClass() 
    { 
     base.LastName = "Derived Class"; 
    } 
} 

internal class Tester 
{ 
    private static void Main(string[] args) 
    { 
     BaseClass objBaseClass = new BaseClass(); 
     Console.WriteLine("First Name : " + objBaseClass.FirstName); 
     Console.WriteLine("Last Name : " + objBaseClass.LastName); 

     DerivedClass objDerivedClass = new DerivedClass(); 
     Console.WriteLine("First Name : " + objDerivedClass.FirstName); 
     Console.WriteLine("Last Name : " + objDerivedClass.LastName); 

     BaseClass objBaseDerivedClass = new DerivedClass(); 
     Console.WriteLine("First Name : " + objBaseDerivedClass.FirstName); 
     Console.WriteLine("Last Name : " + objBaseDerivedClass.LastName); 

     Console.ReadKey(); 
    } 
} 

O/P Имя: Базовый класс

Фамилия: Базовый класс

Имя: Базовый класс

Фамилия: Производный Класс

Имя: базовый класс

Фамилия: Производный класс

Сообщите мне, если это поможет.

+0

Pank, спасибо за объяснение, но в этом случае я пользуюсь внешней библиотекой и не имею доступа для изменения источника. Также я хочу получить доступ к дочерним свойствам из родительской ссылки. Объекты, которые входят, все равно будут дочерними объектами. –

0

Если я правильно вас понял (- я предполагаю, что Parent базовый класс, от которого Child0Child1 и т.д. унаследовать.) - вы просто не хватает декларацию prop1 в родителя. Это не будет мешать, оно просто будет отменено.

Проверьте этот пример (который возвращает «дочерняя строка») и обратите внимание, что child передается методу, который ожидает экземпляр ParentClass.

public partial class Form1 : Form 
{ 
    public Form1() 
    { 
     InitializeComponent(); 
     ChildClass child = new ChildClass(); 
     Text = ParentClass.mymethod(child); 
    } 
} 

class ParentClass 
{ 
    public virtual string s { get { return "parent string"; } } 

    public static string mymethod(ParentClass parent) 
    { 
     return parent.s; 
    } 
} 

class ChildClass : ParentClass 
{ 
    public override string s { get { return "child string"; } } 
} 
Смежные вопросы