public SPModel( IConstraintElementsAbstractFactory constraintElementsAbstractFactory, IConstraintsAbstractFactory constraintsAbstractFactory, ICrossJoinElementsAbstractFactory crossJoinElementsAbstractFactory, ICrossJoinsAbstractFactory crossJoinsAbstractFactory, IDependenciesAbstractFactory dependenciesAbstractFactory, IIndexElementsAbstractFactory indexElementsAbstractFactory, IIndicesAbstractFactory indicesAbstractFactory, IObjectiveFunctionsAbstractFactory objectiveFunctionsAbstractFactory, IParameterElementsAbstractFactory parameterElementsAbstractFactory, IParametersAbstractFactory parametersAbstractFactory, IVariablesAbstractFactory variablesAbstractFactory, ISPInputContext SPInputContext) { this.SPInputContext = SPInputContext; this.Model = dependenciesAbstractFactory.CreateModelFactory().Create(); // Indices // a this.a = indicesAbstractFactory.CreateaFactory().Create( this.SPInputContext.ActiveDays .Select(x => indexElementsAbstractFactory.CreateaIndexElementFactory().Create( x.Key.Value.Value, x.Value)) .ToImmutableList()); // d this.d = indicesAbstractFactory.CreatedFactory().Create( this.SPInputContext.Days .Select(x => indexElementsAbstractFactory.CreatedIndexElementFactory().Create( x.Key.Value.Value, x.Value)) .ToImmutableList()); // p this.p = indicesAbstractFactory.CreatepFactory().Create( this.SPInputContext.PatientGroups .Select(x => indexElementsAbstractFactory.CreatepIndexElementFactory().Create((PositiveInt)x)) .ToImmutableList()); // s this.s = indicesAbstractFactory.CreatesFactory().Create( this.SPInputContext.SurgeonGroups .Entry .Where(x => x.Resource is Organization) .Select(x => indexElementsAbstractFactory.CreatesIndexElementFactory().Create((Organization)x.Resource)) .ToImmutableList()); // w this.w = indicesAbstractFactory.CreatewFactory().Create( this.SPInputContext.Wards .Select(x => x.Item1) .Select(x => indexElementsAbstractFactory.CreatewIndexElementFactory().Create(x)) .ToImmutableList()); // Cross joins // pa this.pa = crossJoinsAbstractFactory.CreatepaFactory().Create( this.p.Value .SelectMany(b => this.a.Value, (a, b) => crossJoinElementsAbstractFactory.CreatepaCrossJoinElementFactory().Create(a, b)) .ToImmutableList()); // sa this.sa = crossJoinsAbstractFactory.CreatesaFactory().Create( this.s.Value .SelectMany(b => this.a.Value, (a, b) => crossJoinElementsAbstractFactory.CreatesaCrossJoinElementFactory().Create(a, b)) .ToImmutableList()); // wd this.wd = crossJoinsAbstractFactory.CreatewdFactory().Create( this.w.Value .SelectMany(b => this.d.Value, (a, b) => crossJoinElementsAbstractFactory.CreatewdCrossJoinElementFactory().Create(a, b)) .ToImmutableList()); // Parameters // A(p, d) this.A = parametersAbstractFactory.CreateAFactory().Create( this.SPInputContext.PatientGroupDaySubsetActiveDays .Select(x => parameterElementsAbstractFactory.CreateAParameterElementFactory().Create( this.p.GetElementAt((PositiveInt)x.Item1), this.d.GetElementAt(x.Item2), this.a.GetElementAt(x.Item3))) .ToImmutableList()); // BEDS this.BEDS = parametersAbstractFactory.CreateBEDSFactory().Create( (PositiveInt)this.SPInputContext.NumberBeds); // BLOCKS this.BLOCKS = parametersAbstractFactory.CreateBLOCKSFactory().Create( (PositiveInt)this.SPInputContext.NumberBlocks); // dur(p) this.dur = parametersAbstractFactory.CreatedurFactory().Create( this.SPInputContext.PatientGroupSurgeryDurations .Select(x => parameterElementsAbstractFactory.CreatedurParameterElementFactory().Create( this.p.GetElementAt((PositiveInt)x.Key), x.Value)) .ToImmutableList()); // LB(p) this.LB = parametersAbstractFactory.CreateLBFactory().Create( this.SPInputContext.PatientGroupNumberPatientLowerBounds .Select(x => parameterElementsAbstractFactory.CreateLBParameterElementFactory().Create( this.p.GetElementAt((PositiveInt)x.Key), (PositiveInt)x.Value)) .ToImmutableList()); // LENGTH this.LENGTH = parametersAbstractFactory.CreateLENGTHFactory().Create( this.SPInputContext.TimeBlockLength); // P(s) this.Ps = parametersAbstractFactory.CreatePsFactory().Create( this.SPInputContext.SurgeonGroupSubsetPatientGroups .Select(x => parameterElementsAbstractFactory.CreatePsParameterElementFactory().Create( this.s.GetElementAt(x.Key), this.p.GetElementAt((PositiveInt)x.Value))) .ToImmutableList()); // P(w) this.Pw = parametersAbstractFactory.CreatePwFactory().Create( this.SPInputContext.WardSubsetPatientGroups .Select(x => parameterElementsAbstractFactory.CreatePwParameterElementFactory().Create( this.w.GetElementAt(x.Key), this.p.GetElementAt((PositiveInt)x.Value))) .ToImmutableList()); // r this.r = parametersAbstractFactory.CreaterFactory().Create( this.SPInputContext.PatientGroupProfits .Select(x => parameterElementsAbstractFactory.CreaterParameterElementFactory().Create( this.p.GetElementAt((PositiveInt)x.Key), x.Value)) .ToImmutableList()); // UB(p) this.UB = parametersAbstractFactory.CreateUBFactory().Create( this.SPInputContext.PatientGroupNumberPatientUpperBounds .Select(x => parameterElementsAbstractFactory.CreateUBParameterElementFactory().Create( this.p.GetElementAt((PositiveInt)x.Key), (PositiveInt)x.Value)) .ToImmutableList()); // Variables // x(p, a) this.x = variablesAbstractFactory.CreateSPxFactory().Create( dependenciesAbstractFactory.CreateVariableCollectionFactory().Create( model: this.Model, indexSet1: this.p.Value, indexSet2: this.a.Value, lowerBoundGenerator: (a, b) => 0, upperBoundGenerator: null, variableTypeGenerator: (a, b) => VariableType.Integer)); // y(w) this.y = variablesAbstractFactory.CreateSPyFactory().Create( dependenciesAbstractFactory.CreateVariableCollectionFactory().Create( model: this.Model, indexSet1: this.w.Value, lowerBoundGenerator: (a) => 0, upperBoundGenerator: null, variableTypeGenerator: (a) => VariableType.Integer)); // z(s, a) this.z = variablesAbstractFactory.CreateSPzFactory().Create( dependenciesAbstractFactory.CreateVariableCollectionFactory().Create( model: this.Model, indexSet1: this.s.Value, indexSet2: this.a.Value, lowerBoundGenerator: (a, b) => 0, upperBoundGenerator: null, variableTypeGenerator: (a, b) => VariableType.Integer)); // Constraints (2) this.Model.AddConstraint( constraintsAbstractFactory.CreateSPConstraint2Factory().Create( this.w, this.BEDS, this.y) .Value); // Constraints (3) this.Model.AddConstraints( this.wd.Value .Select( i => constraintElementsAbstractFactory.CreateConstraints3ConstraintElementFactory().Create( i.dIndexElement, i.wIndexElement, this.pa, this.A, this.Pw, this.x, this.y) .Value)); // Constraints (4) this.Model.AddConstraints( this.a.Value .Select( i => constraintElementsAbstractFactory.CreateConstraints4ConstraintElementFactory().Create( i, this.s, this.BLOCKS, this.z) .Value)); // Constraints (5) this.Model.AddConstraints( this.sa.Value .Select( i => constraintElementsAbstractFactory.CreateConstraints5ConstraintElementFactory().Create( i.aIndexElement, i.sIndexElement, this.p, this.dur, this.LENGTH, this.Ps, this.x, this.z) .Value)); // Constraints (6L) this.Model.AddConstraints( this.p.Value .Select( i => constraintElementsAbstractFactory.CreateConstraints6LConstraintElementFactory().Create( i, this.a, this.LB, this.x) .Value)); // Constraints (6U) this.Model.AddConstraints( this.p.Value .Select( i => constraintElementsAbstractFactory.CreateConstraints6UConstraintElementFactory().Create( i, this.a, this.UB, this.x) .Value)); // Objective Function (1) this.Model.AddObjective( objectiveFunctionsAbstractFactory.CreateSPObjectiveFunctionFactory().Create( dependenciesAbstractFactory.CreateObjectiveFactory(), this.pa, this.r, this.x) .Value); }