Пример #1
0
        public void BottomUpRewriter_NumToArith_Partial_FallbackWithPredicate()
        {
            var logger = new StringWriter();

            var burw = new BottomUpRewriter <NumExpr, NumNodeType, ArithExpr, NumWildcardFactory>
            {
                // Leaf nodes
                Leaves =
                {
                    { (Val c) => new Const(c.Value), 1 },
                },

                // Tree patterns
                Rules =
                {
                    { (l,              r) => new Plus(l, r),                    (l, r) => new Add(l, r), 2 },
                    { (a,              b,                c) => new TimesPlus(a, b,  c),              (a, b, c) => new Add(new Mul(a, b), c), 2},
                    { x => new Inc(x), x => new Add(x,   new Const(1)),        2 },
                },

                // Fallback rules
                Fallbacks =
                {
                    { n => new Const(((Times)n).Let(t => t.Left.Eval() * t.Right.Eval())), n => n.Value == NumNodeType.Times, 1 },
                },

                Log = logger
            };

            // Internal tables
            var debugView = burw.DebugView;

            Assert.IsTrue(!string.IsNullOrEmpty(debugView));

            var e = new TimesPlus(
                new Inc(
                    new Times(
                        new Val(2),
                        new Val(3)
                        )
                    ),
                new Times(
                    new Val(4),
                    new Val(5)
                    ),
                new Val(6)
                );

            var res = burw.Rewrite(e);

            Assert.AreEqual("Add(Mul(Add(Const(6), Const(1)), Const(20)), Const(6))", res.ToString());
            Assert.AreEqual(e.Eval(), res.Eval());
        }
Пример #2
0
        public void BottomUpRewriter_NumToArith_Partial_FallbackUnconditional()
        {
            var logger = new StringWriter();

            var burw = new BottomUpRewriter <NumExpr, NumNodeType, ArithExpr, NumWildcardFactory>
            {
                // Leaf nodes
                Leaves =
                {
                    { (Val c) => new Const(c.Value), 1 },
                },

                // Tree patterns
                Rules =
                {
                    { (l,              r) => new Plus(l, r),                    (l, r) => new Add(l, r), 2 },
                    { (a,              b,                c) => new TimesPlus(a, b,  c),              (a, b, c) => new Add(new Mul(a, b), c), 2},
                    { x => new Inc(x), x => new Add(x,   new Const(1)),        2 },
                },

                // Fallback rules
                Fallbacks =
                {
                    { n => new Lazy(() => n.Eval()), 1 },
                },

                Log = logger
            };

            // Internal tables
            var debugView = burw.DebugView;

            Assert.IsTrue(!string.IsNullOrEmpty(debugView));

            var e = new TimesPlus(
                new Inc(
                    new Times(
                        new Val(2),
                        new Val(3)
                        )
                    ),
                new Times(
                    new Val(4),
                    new Val(5)
                    ),
                new Val(6)
                );

            var res = burw.Rewrite(e);

            Assert.IsTrue(res.ToString().Contains("Lazy"));
            Assert.AreEqual(e.Eval(), res.Eval());
        }
Пример #3
0
        public void BottomUpRewriter_ArithToNum()
        {
            var logger = new StringWriter();

            var burw = new BottomUpRewriter <ArithExpr, ArithNodeType, NumExpr, ArithWildcardFactory>
            {
                // Leaf nodes
                Leaves =
                {
                    { (Const c) => new Val(c.Value), 1 },
                },

                // Tree patterns
                Rules =
                {
                    { (l,             r) => new Add(l, r),                      (l, r) => new Plus(l,  r), 2 },
                    { (l,             r) => new Mul(l, r),                      (l, r) => new Times(l, r), 3 },
                    { (a,             b,               c) => new Add(new Mul(a, b), c),                (a, b, c) => new TimesPlus(a, b, c), 4},
                    { x => new Add(x, new Const(1)),   x => new Inc(x),        1 },
                },

                Log = logger
            };

            // Internal tables
            var debugView = burw.DebugView;

            Assert.IsTrue(!string.IsNullOrEmpty(debugView));

            var e = new Add(
                new Mul(
                    new Add(
                        new Mul(
                            new Const(2),
                            new Const(3)
                            ),
                        new Const(1)
                        ),
                    new Mul(
                        new Const(4),
                        new Const(5)
                        )
                    ),
                new Const(6)
                );

            var res = burw.Rewrite(e);

            Assert.AreEqual("TimesPlus(Inc(Times(2, 3)), Times(4, 5), 6)", res.ToString());
            Assert.AreEqual(e.Eval(), res.Eval());
        }
Пример #4
0
        private static BottomUpRewriter <NumTree, Num, NumTree, NumWildcards> GetNumOptimizer()
        {
            var burs = new BottomUpRewriter <NumTree, Num, NumTree, NumWildcards>();

            burs.Leaves.Add <ConstNumTree>(c => c, 1);
            burs.Leaves.Add <ConstNumTree>(c => c, c => c.Value > 0, 1);

            burs.Rules.Add(() => new UnaryNumTree(NumKind.Negate, ConstNumTree.Zero), () => ConstNumTree.Zero, 1);

            burs.Rules.Add(n => new BinaryNumTree(NumKind.Add, n, ConstNumTree.Zero), n => n, 1);
            burs.Rules.Add(n => new BinaryNumTree(NumKind.Add, ConstNumTree.Zero, n), n => n, 1);

            burs.Rules.Add(n => new BinaryNumTree(NumKind.Multiply, n, ConstNumTree.One), n => n, 1);
            burs.Rules.Add(n => new BinaryNumTree(NumKind.Multiply, ConstNumTree.One, n), n => n, 1);

            return(burs);
        }
Пример #5
0
        public void BottomUpRewriter_ArgumentChecking()
        {
#pragma warning disable IDE0034 // Simplify 'default' expression (illustrative of method signature)
            AssertEx.ThrowsException <ArgumentNullException>(() => new BottomUpRewriter <ITree <Bar>, Bar, ITree <Foo>, BarWildcards>(sourceNodeComparer: null), ex => Assert.AreEqual("sourceNodeComparer", ex.ParamName));

            var burs = new BottomUpRewriter <ITree <Bar>, Bar, ITree <Foo>, BarWildcards>();

            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Leaves.Add(default(Expression <Func <ITree <Bar>, ITree <Foo> > >), 1), ex => Assert.AreEqual("convert", ex.ParamName));
            AssertEx.ThrowsException <ArgumentOutOfRangeException>(() => burs.Leaves.Add((ITree <Bar> b) => null, -1), ex => Assert.AreEqual("cost", ex.ParamName));

            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Leaves.Add(default(Expression <Func <ITree <Bar>, ITree <Foo> > >), (ITree <Bar> b) => true, 1), ex => Assert.AreEqual("convert", ex.ParamName));
            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Leaves.Add((ITree <Bar> b) => null, default(Expression <Func <ITree <Bar>, bool> >), 1), ex => Assert.AreEqual("predicate", ex.ParamName));
            AssertEx.ThrowsException <ArgumentOutOfRangeException>(() => burs.Leaves.Add((ITree <Bar> b) => null, (ITree <Bar> b) => true, -1), ex => Assert.AreEqual("cost", ex.ParamName));

            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Rules.Add(pattern: null, () => null, 1), ex => Assert.AreEqual("pattern", ex.ParamName));
            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Rules.Add(() => null, goal: null, 1), ex => Assert.AreEqual("goal", ex.ParamName));
            AssertEx.ThrowsException <ArgumentOutOfRangeException>(() => burs.Rules.Add(() => null, () => null, -1), ex => Assert.AreEqual("cost", ex.ParamName));

            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Rules.Add(pattern: null, (f1) => f1, 1), ex => Assert.AreEqual("pattern", ex.ParamName));
            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Rules.Add((b1) => b1, goal: null, 1), ex => Assert.AreEqual("goal", ex.ParamName));
            AssertEx.ThrowsException <ArgumentOutOfRangeException>(() => burs.Rules.Add((b1) => b1, (f1) => f1, -1), ex => Assert.AreEqual("cost", ex.ParamName));

            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Rules.Add(pattern: null, (f1, f2) => f1, 1), ex => Assert.AreEqual("pattern", ex.ParamName));
            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Rules.Add((b1, b2) => b1, goal: null, 1), ex => Assert.AreEqual("goal", ex.ParamName));
            AssertEx.ThrowsException <ArgumentOutOfRangeException>(() => burs.Rules.Add((b1, b2) => b1, (f1, f2) => f1, -1), ex => Assert.AreEqual("cost", ex.ParamName));

            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Rules.Add(pattern: null, (f1, f2, f3) => f1, 1), ex => Assert.AreEqual("pattern", ex.ParamName));
            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Rules.Add((b1, b2, b3) => b1, goal: null, 1), ex => Assert.AreEqual("goal", ex.ParamName));
            AssertEx.ThrowsException <ArgumentOutOfRangeException>(() => burs.Rules.Add((b1, b2, b3) => b1, (f1, f2, f3) => f1, -1), ex => Assert.AreEqual("cost", ex.ParamName));

            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Fallbacks.Add(default(Expression <Func <ITree <Bar>, ITree <Foo> > >), 1), ex => Assert.AreEqual("convert", ex.ParamName));
            AssertEx.ThrowsException <ArgumentOutOfRangeException>(() => burs.Fallbacks.Add((ITree <Bar> b) => null, -1), ex => Assert.AreEqual("cost", ex.ParamName));

            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Fallbacks.Add(default(Expression <Func <ITree <Bar>, ITree <Foo> > >), (ITree <Bar> b) => true, 1), ex => Assert.AreEqual("convert", ex.ParamName));
            AssertEx.ThrowsException <ArgumentNullException>(() => burs.Fallbacks.Add((ITree <Bar> b) => null, default(Expression <Func <ITree <Bar>, bool> >), 1), ex => Assert.AreEqual("predicate", ex.ParamName));
            AssertEx.ThrowsException <ArgumentOutOfRangeException>(() => burs.Fallbacks.Add((ITree <Bar> b) => null, (ITree <Bar> b) => true, -1), ex => Assert.AreEqual("cost", ex.ParamName));
#pragma warning restore IDE0034 // Simplify 'default' expression

            var mb = new MyBurs();
            mb.Fallbacks.Add(b => null, 1);
            mb.Leaves.Add <ITree <Bar> >(b => null, 1);
            mb.Rules.Add(b => null, f => null, 1);
            Assert.AreEqual(3, mb.Count);
        }
Пример #6
0
        public void BottomUpRewriter_NumToArith_Partial_Irreducible()
        {
            var logger = new StringWriter();

            var burw = new BottomUpRewriter <NumExpr, NumNodeType, ArithExpr, NumWildcardFactory>
            {
                // Leaf nodes
                Leaves =
                {
                    { (Val c) => new Const(c.Value), 1 },
                },

                // Tree patterns
                Rules =
                {
                    { (l,              r) => new Plus(l, r),                    (l, r) => new Add(l, r), 2 },
                    { (a,              b,                c) => new TimesPlus(a, b,  c),              (a, b, c) => new Add(new Mul(a, b), c), 2},
                    { x => new Inc(x), x => new Add(x,   new Const(1)),        2 },
                },

                Log = logger
            };

            // Internal tables
            var debugView = burw.DebugView;

            Assert.IsTrue(!string.IsNullOrEmpty(debugView));

            var e = new TimesPlus(
                new Inc(
                    new Times(
                        new Val(2),
                        new Val(3)
                        )
                    ),
                new Times(
                    new Val(4),
                    new Val(5)
                    ),
                new Val(6)
                );

            Assert.ThrowsException <InvalidOperationException>(() => burw.Rewrite(e));
        }
Пример #7
0
        public void BottomUpRewriter_UnusedWildcard()
        {
            var burs = new BottomUpRewriter <NumTree, Num, NumTree, NumWildcards>();

            Assert.ThrowsException <InvalidOperationException>(() => burs.Rules.Add((a, b, c) => new BinaryNumTree(NumKind.Add, a, b), (a, b, c) => a, 1));
        }