Применима ли модель фабричного дизайна в этой ситуации? - PullRequest
0 голосов
/ 13 ноября 2018
  • taskA, taskB, taskC наследуются от моего класса Task

  • ContextA, ContextA2, ContextB, ContextC наследуются от моего класса Context

Контексты имеют соответствующую задачу в качестве свойства класса:

public abstract class Context
{
    public String CommonProperty { get; set; }

    public abstract void MethodToOverride();
}

public class ContextA : Context
{
    public TaskA Task { get; set; }

    public override void MethodToOverride()
    {
        //do stuff with this.Task and this.CommonProperty
    }
}

public class ContextA2 : Context
{
    public TaskA Task { get; set; }

    public override void MethodToOverride()
    {
        //do stuff with this.Task and this.CommonProperty
    }
}

public class ContextB : Context
{
    public TaskB Task { get; set; }

    public override void MethodToOverride()
    {
        //do stuff with this.Task and this.CommonProperty
    }
}

И так далее ...

При переборе списка задач я хочу создать соответствующий Контекст:

foreach (Task t in tasks)
{
    Context context;

    if (t is TaskA)
    {
        if (condition)
        {
            context = new ContextA() { Task = t as TaskA};
        }
        else
        {
            context = new ContextA2() { Task = t as TaskA };
        }
    }
    else if (t is TaskB)
    {
        context = new ContextB() { Task = t as TaskB };
    }
    else if (t is TaskC)
    {
        context = new ContextC(){ Task = t as TaskC };
    }
    else
    {
        throw new Exception("Unkown Task");
    }

    context.CommonProperty = "value";
    context.MethodToOverride();//Do different things based on the context type
}

Я чувствую, что для этого должен быть более чистый способ, но я не могу понять, как управлять созданием объекта контекста, особенно в случае contextA и contextA2, которые зависят от условия.

Ответы [ 2 ]

0 голосов
/ 14 ноября 2018

Да, подходит заводская модель.

class ContextFactory {
    public create(TaskA t, bool condition) {
        return condition ? new ContextA() { Task = t } : new ContextA2() { Task = t };
    }
    public create(TaskB t) {
        return new ContextB() { Task = t };
    }
    public create(TaskC t) {
        return new ContextC() { Task = t };
    }
}
...
ContextFactory factory = //... new or passed from somewhere
foreach (Task t in tasks) {
    Context context;
    if (t is TaskA) {
        context = factory.create(t as TaskA, condition);
    } else if (t is TaskB) {
        context = factory.create(t as TaskB);
    } else if (t is TaskC)
        context = factory.create(t as TaskC);
    } else {
        throw new Exception("Unkown Task");
    }
    context.CommonProperty = "value";
    context.MethodToOverride();//Do different things based on the context type
}
0 голосов
/ 13 ноября 2018
foreach (Task t in tasks)
{
    Context  context = t.ConstructContext(condition);



    context.CommonProperty = "value";
    context.MethodToOverride();//Do different things based on the context type
}

public asbtract class Task
{
    //whatever might be in here
    public abstract Context ConstructContext();
}

public class TaskA : Task
{
    //NOTE: In my opinion condition should be internal to TaskA and no one else should know about and you should remove the parameter from the method
    // but I don't know where you get it from so I'm leaving it here
    public override Context ConstructContext(bool condition)
    {
        if (condition)
        {
            return new ContextA() { Task = this};
        }
        else
        {
            return new ContextA2() { Task = thid };
        }
    }
}

public class TaskB : Task
{
    public override Context ConstructContext(bool condition)
    {
        //ignore condition which implies it shouldn't really be passed

        return new ContextB() {Task = this};
    }
}

//etc...

Мне действительно не нравится проходить мимо этого условия, на мой взгляд, это запах кода, но из того, что вы сказали, это должно быть что-то внешнее по отношению к задачам.В любом случае это должно удовлетворить ваши потребности

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...