/// <summary> /// Applies backwards the relevant operator effects and operator preconditions to the given target conditions. /// </summary> /// <param name="conditions">Target conditions to be modified.</param> /// <param name="operatorSubstitution">Variables substitution.</param> /// <returns>Preceding conditions.</returns> public IConditions ApplyBackwards(IConditions conditions, ISubstitution operatorSubstitution) { ConditionsCNF expression = (ConditionsCNF)conditions?.GetCNF(); if (expression == null) { return(null); } OperatorSubstitution = operatorSubstitution; Effects.GroundEffectsByCurrentOperatorSubstitution(GroundingManager, operatorSubstitution); if (expression.Parameters != null) { EffectsRelevanceConditionsEvaluator evaluator = new EffectsRelevanceConditionsEvaluator(Effects, GroundingManager); List <ConditionsCNF> subResults = new List <ConditionsCNF>(); IEnumerable <ISubstitution> expressionSubstitutions = GroundingManager.GenerateAllLocalSubstitutions(expression.Parameters); expression.Parameters = null; foreach (var expressionSubstitution in expressionSubstitutions) { // do backward apply only when the effects are relevant to the current grounding of the expression if (evaluator.Evaluate(expression, operatorSubstitution, expressionSubstitution)) { subResults.Add(ApplyBackwardsImpl(expression, expressionSubstitution)); } } return(ConstructCNFFromDisjunction(subResults)); } return(ApplyBackwardsImpl(expression, new Substitution())); }
/// <summary> /// Collects relevant when effects for the specified conditions. /// </summary> /// <param name="expression">Conditions in CNF.</param> /// <returns>List of relevant when effects.</returns> private List <WhenEffect> GetRelevantWhenEffectsForConditions(ConditionsCNF expression) { List <int> relevantWhenEffectsIndices = new List <int>(); EffectsRelevanceConditionsEvaluator relevanceEvaluator = new EffectsRelevanceConditionsEvaluator(Effects, GroundingManager); relevanceEvaluator.Evaluate(expression, new Substitution(), ExpressionSubstitution, relevantWhenEffectsIndices); // empty substitution here because effects already grounded List <WhenEffect> relevantWhenEffects = new List <WhenEffect>(); relevantWhenEffectsIndices.ForEach(index => relevantWhenEffects.Add(Effects.WhenEffects[index])); return(relevantWhenEffects); }