object INumExprVisitor <object> .VisitBinExpr(NumBinExpr numBinExpr)
 {
     this.AppendLine(numBinExpr.Kind.ToString());
     this.Push();
     numBinExpr.Left.Apply(this);
     numBinExpr.Right.Apply(this);
     this.Pop();
     return(null);
 }
        public static NumExpr ExpToTree(string exp)
        {
            exp = exp.SpaceDelite();
            NumBinExpr tree = new NumBinExpr();
            int        BracketCounter = 0, minPrior = 20, indexMinPrior = -1;

            for (int i = 0; i < exp.Length; ++i)
            {
                if (exp[0] == '(' && exp[exp.Length - 1] == ')' && exp.BracketsCanBeDeleted())
                {
                    exp = exp.Remove(exp.Length - 1);
                    exp = exp.Substring(1);
                }
                if (exp[i] == '(')
                {
                    ++BracketCounter;
                }
                else if (exp[i] == ')')
                {
                    --BracketCounter;
                }
                else
                {
                    if (BracketCounter == 0 && !Char.IsLetterOrDigit(exp[i]))
                    {
                        int tmpOpPrior = _priorityByChar[exp[i]];
                        if (minPrior >= _priorityByChar[exp[i]])
                        {
                            minPrior      = tmpOpPrior;
                            indexMinPrior = i;
                        }
                    }
                }
            }
            if (indexMinPrior != -1)
            {
                tree.Kind  = _opByChar[exp[indexMinPrior]];
                tree.Left  = ExpToTree(exp.Remove(indexMinPrior));
                tree.Right = ExpToTree(exp.Substring(indexMinPrior + 1));
            }
            else
            {
                for (int i = 0; i < exp.Length; i++)
                {
                    if (!Char.IsDigit(exp[i]))
                    {
                        return(new NumVarExpr(exp));
                    }
                }
                return(new NumConstExpr(Int32.Parse(exp)));
            }
            return(tree);
        }
        string GetChildStr(NumBinExpr curr, NumExpr child)
        {
            var    bin = child as NumBinExpr;
            string result;

            if (bin != null && _priorityByOp[curr.Kind] > _priorityByOp[bin.Kind])
            {
                result = $"({child.Apply(this)})";
            }
            else
            {
                result = child.Apply(this);
            }

            return(result);
        }
 string INumExprVisitor <string> .VisitBinExpr(NumBinExpr curr)
 {
     return(string.Join(" ", this.GetChildStr(curr, curr.Left), _strByOp[curr.Kind], this.GetChildStr(curr, curr.Right)));
 }
 string INumExprVisitor <string> .VisitBinExpr(NumBinExpr numBinExpr)
 {
     return(numBinExpr.Kind.ToString());
 }