コード例 #1
0
        /// <summary>
        /// Checks the equality of objects.
        /// </summary>
        /// <param name="obj">Object to be checked.</param>
        /// <returns>True if the objects are equal, false otherwise.</returns>
        public override bool Equals(object obj)
        {
            OrExpression other = obj as OrExpression;

            if (other == null)
            {
                return(false);
            }
            return(CollectionsEquality.Equals(Children, other.Children));
        }
コード例 #2
0
        /// <summary>
        /// Visits and transforms the expression.
        /// </summary>
        /// <param name="expression">Source expression.</param>
        /// <returns>Transformed expression.</returns>
        public override IExpression Visit(OrExpression expression)
        {
            List <IExpression> children = new List <IExpression>();

            foreach (var child in expression.Children)
            {
                children.Add(child.Accept(this));
            }

            HashSet <IExpression>   primitives     = new HashSet <IExpression>();
            HashSet <AndExpression> andExpressions = new HashSet <AndExpression>();

            foreach (var element in children)
            {
                AndExpression andExpression = element as AndExpression;
                if (andExpression != null)
                {
                    andExpressions.Add(andExpression);
                    continue;
                }

                OrExpression orExpression = element as OrExpression;
                if (orExpression != null)
                {
                    foreach (var orChild in orExpression.Children)
                    {
                        primitives.Add(orChild);
                    }
                }
                else
                {
                    // predicate, equals, numericCompare, forall, exists
                    primitives.Add(element);
                }
            }

            OrExpression primitivesClause = new OrExpression(new List <IExpression>(primitives));

            if (andExpressions.Count == 0)
            {
                return(primitivesClause);
            }

            List <OrExpression> clauses = new List <OrExpression>();

            if (primitives.Count != 0)
            {
                clauses.Add(primitivesClause);
            }

            return(new AndExpression(DistributeDisjunctions(new List <AndExpression>(andExpressions), clauses)));
        }
コード例 #3
0
        /// <summary>
        /// Visits and performs a property count on predicate expression.
        /// </summary>
        /// <param name="expression">Predicate expression.</param>
        /// <returns>Tuple (property satisfied count, property not satisfied count).</returns>
        public Tuple <double, double> Visit(OrExpression expression)
        {
            double positiveValue = 0.0;
            double negativeValue = 0.0;

            foreach (var child in expression.Children)
            {
                var childPropertyCounts = child.Accept(this);
                positiveValue = Math.Max(positiveValue, childPropertyCounts.Item1);
                negativeValue = Math.Max(negativeValue, childPropertyCounts.Item2);
            }

            return(Tuple.Create(positiveValue, negativeValue));
        }
コード例 #4
0
        /// <summary>
        /// Visits and performs a property count on predicate expression.
        /// </summary>
        /// <param name="expression">Predicate expression.</param>
        /// <returns>Tuple (property satisfied count, property not satisfied count).</returns>
        public Tuple <int, int> Visit(OrExpression expression)
        {
            int minFulfilled    = int.MaxValue;
            int minNotFulfilled = int.MaxValue;

            foreach (var child in expression.Children)
            {
                var childPropertyCounts = child.Accept(this);
                minFulfilled    = Math.Min(minFulfilled, childPropertyCounts.Item1);
                minNotFulfilled = Math.Min(minNotFulfilled, childPropertyCounts.Item2);
            }

            return(Tuple.Create(minFulfilled, minNotFulfilled));
        }
コード例 #5
0
        /// <summary>
        /// Visits and transforms the expression.
        /// </summary>
        /// <param name="expression">Source expression.</param>
        /// <returns>Transformed expression.</returns>
        public override IExpression Visit(OrExpression expression)
        {
            List <IExpression> arguments = new List <IExpression>();

            foreach (var child in expression.Children)
            {
                arguments.Add(child.Accept(this));
            }

            if (IsNegating)
            {
                return(new AndExpression(arguments));
            }
            return(new OrExpression(arguments));
        }
コード例 #6
0
        /// <summary>
        /// Distributes disjunctions deeper into the expression (by deMorgan laws) - i.e. we need to push ORs inside the expression and pull ANDs
        /// outside the expression to get the CNF representation. We also filter out duplicates in the clauses and conjunctions (indepotence property).
        /// </summary>
        /// <param name="andExpressions">Conjunctions on the given level.</param>
        /// <param name="clauses">Disjunctions on the given level.</param>
        /// <returns>List of clauses or literals.</returns>
        private static List <IExpression> DistributeDisjunctions(List <AndExpression> andExpressions, List <OrExpression> clauses)
        {
            foreach (var andExpr in andExpressions)
            {
                List <OrExpression> newClauses = new List <OrExpression>();
                foreach (var andElem in andExpr.Children)
                {
                    HashSet <IExpression> andElemItems = new HashSet <IExpression>();

                    OrExpression orExpr = andElem as OrExpression;
                    if (orExpr != null)
                    {
                        orExpr.Children.ForEach(child => andElemItems.Add(child));
                    }
                    else
                    {
                        andElemItems.Add(andElem);
                    }

                    if (clauses.Count == 0)
                    {
                        newClauses.Add(new OrExpression(new List <IExpression>(andElemItems)));
                    }
                    else
                    {
                        foreach (var clause in clauses)
                        {
                            HashSet <IExpression> newOrChildren = new HashSet <IExpression>();
                            clause.Children.ForEach(child => newOrChildren.Add(child));
                            newOrChildren.UnionWith(andElemItems);
                            newClauses.Add(new OrExpression(new List <IExpression>(newOrChildren)));
                        }
                    }
                }
                clauses = newClauses;
            }

            HashSet <IExpression> clausesList = new HashSet <IExpression>();

            clauses.ForEach(clause => clausesList.Add(clause));
            return(new List <IExpression>(clausesList));
        }
コード例 #7
0
        /// <summary>
        /// Visits the expression.
        /// </summary>
        /// <param name="expression">Expression.</param>
        public override void Visit(OrExpression expression)
        {
            expression.Children.ForEach(child => child.Accept(this));

            ClauseCNF clause = new ClauseCNF();

            for (int i = 0; i < expression.Children.Count; ++i)
            {
                LiteralCNF literal = Stack.Pop() as LiteralCNF;
                if (literal != null)
                {
                    clause.Add(literal);
                }
                else
                {
                    Debug.Assert(false, "Source expression not in CNF!");
                }
            }
            Stack.Push(clause);
        }