Как неявно реализовать метод в обобщенном классе, производном от абстрактного? - PullRequest
3 голосов
/ 27 декабря 2011

Я пытаюсь получить список классов, которые реализуют универсальный класс и могут получить доступ к некоторым членам GenericClass через абстрактную базу. Вот где я сейчас:

public abstract class AbstractParent: UserControl
{
    public abstract AAction Action { get; set; }
}

public abstract class GenericBase<ActionType> : AbstractParent 
{
    protected ActionType _action;

    new public ActionType Action
    {
        set { _action = value; }
        get { return _action; }
    }
}

Чтобы получить список экземпляров GenericBase <>, я использую List<AbstractParent>

Проблема в том, что мне нужно открытое свойство genericType (передаваемое производным классом из GenericBase).

Ошибка на данный момент Action hides inherited abstract member Action.get. Я знаю, что у меня может быть абстрактное свойство и реализация или модификатор new в производном свойстве. Оба не вписываются в эту ситуацию.

пример того, что я хочу:

GenericBase<BlueAction> blueClass;
blueClass.Action <- I want this member to be of BlueAction type

Ответы [ 2 ]

2 голосов
/ 27 декабря 2011
public interface IActionable 
{
  public ActionType Action { get; }
}

public class ActionableWrapper : IActionable
{ 

  private ActionType _action;

  public ActionableWrapper(IActionable Actionable)
  {
    this._action = Actionable;
  }

  new public ActionType Action 
  { 
    get { return _action; } 
  } 
} 

public class BlueAction: IActionable
{
  public ActionType Action { get; }
}

Это делает то, что вы хотите, если не используете дженерики. Так как я не могу понять, ПОЧЕМУ вы хотели бы получить List<ActionableWrapper>, тогда как вместо использования обобщений вы могли бы просто использовать интерфейсы и сделать это просто List<IActionable>.

I am trying to have a List of classes that implement a generic class and be able to access some members of the GenericClass through the abstract base.

Используя Linq, вы легко можете сделать это в любом случае (на своем примере):

List<AbstractParent> AbstractParentCollection = new List<AbstractParent>();
GenericBase<BlueAction> blueClass;     
AbstractParentCollection.Add(blueClass);
AbStractParentCollection.Typeof(GenericBase<BlueAction>).First().Action...
1 голос
/ 27 декабря 2011

Может ли ваш AbstractParent быть переработан для использования ActionType:

public abstract class AbstractParent<ActionType>
{
    public abstract Action<ActionType> Action { get; set; }
}

тогда ваш унаследованный класс может переопределить, если необходимо:

public override Action<ActionType> Action

Обновление

Альтернативой является использование ActionType нового интерфейса, такого как IActionType. Свойство return из базового класса будет интерфейсом, и это не обязательно должно быть переопределено в унаследованном классе.

Вот полная структура класса / интерфейса:

public interface IAction
{
}

public abstract class AbstractParent
{
    public abstract IAction Action { get; set; }
}

public abstract class GenericBase<T> : AbstractParent where T : IAction
{
    protected IAction _action;

    public override IAction Action
    {
        get
        {
            return _action;
        }
        set
        {
            _action = value;
        }
    }
}
...