Как правило, вы не должны указывать фабрике, какой конкретный тип создать. Вы должны предоставить ему информацию, необходимую для принятия этого решения. Я не говорю, что это не может быть отношение 1: 1, просто вызывающая сторона не должна указывать фабрике, чтобы она создавала конкретный конкретный тип.
Представьте, что у вас есть объект Student
со свойством Grade
. У вас также есть фабрика, которая производит ISchool
, и конкретные реализации ElementarySchool
, MiddleSchool
и HighSchool
. Теперь у вас может быть 3 метода: CreateElementarySchool()
, CreateMiddleSchool()
и CreateHighSchool()
, но тогда вызывающий должен решить, какой из них ему нужен.
Лучше всего иметь метод, который использует некоторую информацию для создания школы. Например: CreateSchoolForGrade(grade)
. Внутри фабрика будет иметь логику, которая определяет, какой тип бетона соответствует марке.
В вашем случае, если у вас есть набор из 2 типов для выбора на веб-форме, вы можете принять тип (скажем, варианты - Империя или Повстанцы). Вы можете получить перечисление:
public enum Faction
{
Empire,
Rebels
}
, а затем заводской метод:
public IFaction CreateFaction(Faction faction)
{
switch (faction)
{
case Faction.Empire:
return new EmpireFaction();
case Faction.Rebels:
return new RebelsFaction();
default:
throw new NotImplementedException();
}
}
Теперь представьте, что вы удалили EmpireFaction, заменив ее EmpireFactionV2. Вам нужно только изменить свою фабрику, а вызывающему абоненту все равно:
public IFaction CreateFaction(Faction faction)
{
switch (faction)
{
case Faction.Empire:
return new EmpireFactionV2();
case Faction.Rebels:
return new RebelsFaction();
default:
throw new NotImplementedException();
}
}