private async Task <InferenceResults <Tval> > ReduceDomains(ConstraintSatisfactionProblem <Tval> csp, Queue <Tuple <Variable <Tval>, Variable <Tval> > > queueOfArcs, InferenceResults <Tval> inference = null, bool stopAtInconsistency = true) { inference = inference ?? new InferenceResults <Tval>(); while (queueOfArcs.Count > 0) { Tuple <Variable <Tval>, Variable <Tval> > arc = queueOfArcs.Dequeue(); Variable <Tval> X = arc.Item1, Y = arc.Item2; if (await Revise(csp, X, Y, inference)) { if (X.GetDomain().Size() == 0) { inference.InconsistencyFound(X); if (stopAtInconsistency) { return(inference); } } foreach (Variable <Tval> neighbour in csp.GetNeighboursOf(X)) { queueOfArcs.Enqueue(new Tuple <Variable <Tval>, Variable <Tval> >(neighbour, X)); } } } return(inference); }
public override async Task <InferenceResults <Tval> > RemoveVariable(ConstraintSatisfactionProblem <Tval> csp, Assignment <Tval> assignment, Variable <Tval> variable, Domain <Tval> default_domain = null) { if (csp == null) { throw new ArgumentNullException("csp"); } if (assignment == null) { throw new ArgumentNullException("assignment"); } if (variable == null) { throw new ArgumentNullException("variable"); } if (assignment.HasBeenAssigned(variable)) { Tval oldValue = assignment.ValueOf(variable); assignment.RemoveAssignment(variable); List <Variable <Tval> > neighbours = csp.GetNeighboursOf(variable); foreach (Variable <Tval> v in neighbours) { // to preserve consistency of the domains it is neccessary // to add back the old value only when it's fitting if (!assignment.HasBeenAssigned(v) || assignment.ValueOf(v).Equals(oldValue)) { v.GetDomain().GetValues().Add(oldValue); } } variable.UpdateDomain(default_domain ?? new Domain <Tval>()); } return(await inferenceStrategy.Infer(csp, false)); // there are difficult edge cases that an inference limited // on the neighbours can't solve // return inferenceStrategy.Infer(csp, variable, default(Tval), null, false); }