Пример #1
0
    public override Operator toExplicit()
    {
        BinaryOperator o = new OperatorOr();

        o.setLeftOperand(m_left.toExplicit());
        o.setRightOperand(m_left.toExplicit());

        return o;
    }
    /**
     * Constructs an Operator based on a string. With the exception of possible
     * superfluous parentheses and whitespace, the resulting operator is such
     * that getFromString(s).toString() == s. The input string must respect the
     * following BNF grammar (which corresponds to LTL + first-order;
     * parentheses are important):
     * <ol>
     * <li>string := atom | binary_op | unary_op | quantified
     * <li>binary_op := (string) bin_operator (string)
     * <li>unary_op := un_operator (string)
     * <li>quantified := [qualif_var] (string) | &lt;qualif_var&gt; (string)
     * <li>bin_operator := &amp; | -&gt; | the "pipe" character | U | = | &lt; |
     * &gt; | -
     * <li>un_operator := ! | G | X | F
     * <li>qualif_var := atom qualif (there is a whitespace character between
     * atom and qualif)
     * <li>atom := any literal composed of alphanumerical characters, with the
     * exception of reserved sequences such as operators
     * <li>qualif:= any literal composed of alphanumerical characters, with the
     * exception of reserved sequences such as operators
     * </ol>
     *
     * @param s
     *            The input string
     * @param domains
     *            A map from a set of paths to a set of values (atoms), providing
     *            finite domains for quantifiers. This parameter is facultative;
     *            domains need to be provided only when quantifiers need to be
     *            expanded into explicit conjunctions/disjunctions of values, or
     *            when messages must be generated (instead of monitored).
     *
     * @return An Operator equivalent to the string passed as an argument, null
     *         if the string does not correspond to a valid Operator.
     */
    public static Operator parseFromString(string s, IDictionary<string, HashSet<Constant>> domains)
    {
        bool flag = false;
        int quantRight = 0, parLeft = 0;
        Operator o = null, o2 = null;
        FOQuantifier foq = null;
        UnaryOperator uo = null;
        BinaryOperator bo = null;
        Atom a = null;

        // First removes/converts extra whitespace
        s = LTLStringParser.formatString(s);

        string sTrim = s.Trim();

        if (sTrim.Length == 0)
        {
            return null;
        }

        // Handles first-order quantifiers
        flag = false;

        if (sTrim[0] == '[')
        {
            foq = new FOForAll();
            quantRight = sTrim.IndexOf("]");
            flag = true;
        }

        if (sTrim[0] == '<')
        {
            foq = new FOExists();
            quantRight = sTrim.IndexOf(">");
            flag = true;
        }

        if (flag)
        {
            Regex r = new Regex("^(\\w+)\\s*(.*)$");
            MatchCollection m = r.Matches(sTrim.Substring(1, quantRight - 1));

            if (m.Count > 0)
            {
                Match m2 = m[0];
                GroupCollection g = m2.Groups;
                Atom qvar = new Atom(g[1].ToString());
                string qualifier = g[2].ToString();

                foq.setQuantifiedVariable(qvar);
                foq.setQualifier(qualifier);

                if (domains != null)
                {
                    // If a domain is provided, attaches it to the quantifier
                    HashSet<Constant> dom = new HashSet<Constant>();

                    foreach (KeyValuePair<string, HashSet<Constant>> con in domains)
                    {
                        if (con.Key == qualifier)
                        {
                            dom = con.Value;
                        }
                    }

                    foq.setDomain(dom);
                }
            }

            //foq.setQualifiedVariable(sTrim.substring(1, quantRight));
            parLeft = sTrim.IndexOf("(", (quantRight + 1));
            //parRight = sTrim.indexOf(")", parLeft);
            o = parseFromString(sTrim.Substring((parLeft + 1), sTrim.Length - 1 - (parLeft + 1)), domains);
            foq.setOperand(o);

            return foq;
        }

        // Handles unary operators
        flag = false;

        if (sTrim.Substring(0, 1) == "!")
        {
            uo = new OperatorNot();
            flag = true;
        }

        if (sTrim.Substring(0, 1) == "F")
        {
            uo = new OperatorF();
            flag = true;
        }

        if (sTrim.Substring(0, 1) == "G")
        {
            uo = new OperatorG();
            flag = true;
        }

        if (sTrim.Substring(0, 1) == "X")
        {
            uo = new OperatorX();
            flag = true;
        }

        if (sTrim.Length >= 2)
        {
            // This is for CTL, nothing to do here
        }

        if (flag)
        {
            parLeft = sTrim.IndexOf("(");
            o = parseFromString(sTrim.Substring((parLeft + 1), sTrim.Length - 1 - (parLeft + 1)), domains);
            uo.setOperand(o);

            return uo;
        }

        // Handles binary operators
        flag = false;

        if (sTrim[0] == '(')
        {
            // At this point in the method, if first char is a "(",
            // the formula is necessarily a binary operator
            int parNum = 0;
            string sLeft = "", sRight = "";
            string binaryOp = "";
            Regex r = new Regex("(\\(|\\))");
            MatchCollection m = r.Matches(sTrim);

            int mend = -1;
            for (int i = 0; i < m.Count; i++)
            {
                Match m2 = m[i];
                mend = m[i].Groups[0].Index + m[i].Groups[0].Length;

                GroupCollection g = m2.Groups;

                if (g[0].ToString().Equals("("))
                {
                    parNum++;
                }

                else
                {
                    parNum--;
                }

                if (parNum == 0)
                {
                    sLeft = sTrim.Substring(1, mend - 1 - 1);
                    break;
                }
            }

            parLeft = sTrim.IndexOf("(", mend);
            int left_var = mend + 1;
            binaryOp = sTrim.Substring(left_var, parLeft - left_var - 1).Trim();
            sRight = sTrim.Substring(parLeft + 1, sTrim.Length - 1 - (parLeft + 1)).Trim();
            o = parseFromString(sLeft, domains);
            o2 = parseFromString(sRight, domains);

            if (binaryOp == "&")
            {
                bo = new OperatorAnd();
                flag = true;
            }

            if (binaryOp == "|")
            {
                bo = new OperatorOr();
                flag = true;
            }

            if (binaryOp == "=")
            {
                bo = new OperatorEquals(o, o2);
                flag = true;
            }

            if (binaryOp == "->")
            {
                bo = new OperatorImplies(o, o2);
                flag = true;
            }

            if (binaryOp == "-")
            {
                bo = new OperatorMinus(o, o2);
                flag = true;
            }

            if (binaryOp == "<")
            {
                bo = new OperatorSmallerThan(o, o2);
                flag = true;
            }

            if (binaryOp == "<=")
            {
                bo = new OperatorSmallerThan(o, o2, true);
                flag = true;
            }

            if (binaryOp == ">")
            {
                bo = new OperatorGreaterThan(o, o2);
                flag = true;
            }

            if (binaryOp == ">=")
            {
                bo = new OperatorGreaterThan(o, o2, true);
                flag = true;
            }

            if (binaryOp == "U")
            {
                bo = new OperatorU(o, o2);
                flag = true;
            }

            if (binaryOp == "V")
            {
                bo = new OperatorV(o, o2);
                flag = true;
            }

            if (flag)
            {
                return bo;
            }
        }

        else
        {
            // At this point, the only case left is that of a single atom
            // (either a constant or a variable)
            if (sTrim[0] == '{')
            {
                // Constants are surrounded by braces
                a = new Constant(sTrim.Substring(1, sTrim.Length - 1 - 1));
            }

            else if (sTrim[0] == '/')
            {
                // XPaths are surrounded by forward slashes
                a = new ConstantPath(sTrim.Substring(1, sTrim.Length - 1 - 1));
            }

            else
            {
                // Otherwise, we have an atom
                a = new Atom(sTrim);
            }

            return a;
        }

        // Down there, none of the previous cases has fired: return o, which is
        // null
        System.Diagnostics.Debug.Assert (false);
        return o;
    }
Пример #3
0
    public override Operator toExplicit()
    {
        if (m_domain == null || m_domain.Count == 0)
        {
            return null;
        }

        BinaryOperator bo = new OperatorOr();
        bool first = true;

        foreach (Atom a in m_domain)
        {
            Operator o = m_operand.evaluate(m_quantifiedVariable, a);

            if (m_domain.Count == 1)
            {
                return o;
            }

            if (first)
            {
                first = false;
                bo.setLeftOperand(o);

                continue;
            }

            if (bo.getRightOperand() == null)
            {
                bo.setRightOperand(o);
            }

            else
            {
                BinaryOperator newbo = new OperatorOr();

                newbo.setLeftOperand(bo);
                newbo.setRightOperand(o);
                bo = newbo;
            }
        }

        return bo;
    }
Пример #4
0
    public HashSet<GeneratorNode> spawn(OperatorOr op)
    {
        HashSet<GeneratorNode> spawnedSet, outSet = new HashSet<GeneratorNode>();

        // Do for left operand
        GeneratorNode wn = new GeneratorNode(this);
        Operator o2 = op.getLeftOperand();

        wn.addToGamma(o2);
        spawnedSet = wn.spawn();

        foreach (GeneratorNode gn in spawnedSet)
        {
            outSet.Add(gn);
        }

        // Do for right operand
        wn = new GeneratorNode(this);
        o2 = op.getRightOperand();
        wn.addToGamma(o2);
        spawnedSet = wn.spawn();

        if (spawnedSet != null)
        {
            foreach (GeneratorNode gn in spawnedSet)
            {
                outSet.Add(gn);
            }
        }

        return outSet;
    }