Changed minus operator to plus and unary minus.

All unit tests are converted to the new tree representation.
parent 1b1b7bcf
...@@ -274,15 +274,18 @@ class Parser(BisonParser): ...@@ -274,15 +274,18 @@ class Parser(BisonParser):
def on_binary(self, target, option, names, values): def on_binary(self, target, option, names, values):
""" """
binary : exp PLUS exp binary : exp PLUS exp
| exp MINUS exp
| exp TIMES exp | exp TIMES exp
| exp DIVIDE exp | exp DIVIDE exp
| exp POW exp | exp POW exp
| exp MINUS exp
""" """
if 0 <= option < 5: # rule: exp PLUS exp if 0 <= option < 4: # rule: exp {PLUS,TIMES,DIVIDES,POW} exp
return Node(values[1], values[0], values[2]) return Node(values[1], values[0], values[2])
if option == 4: # rule: exp MINUS exp
return Node('+', values[0], Node('-', values[2]))
raise BisonSyntaxError('Unsupported option %d in target "%s".' raise BisonSyntaxError('Unsupported option %d in target "%s".'
% (option, target)) # pragma: nocover % (option, target)) # pragma: nocover
......
...@@ -98,6 +98,28 @@ def run_expressions(base_class, expressions, fail=True, silent=False, ...@@ -98,6 +98,28 @@ def run_expressions(base_class, expressions, fail=True, silent=False,
raise raise
def apply_expressions(base_class, expressions, fail=True, silent=False,
**kwargs):
parser = ParserWrapper(base_class, **kwargs)
for exp, times, out in expressions:
res = None
try:
res = parser.run([exp] + list('@' * times))
assert res == out
except: # pragma: nocover
if not silent:
print >>sys.stderr, 'error: %s gives %s, but expected: %s' \
% (exp, str(res), str(out))
if not silent and hasattr(res, 'nodes'):
print >>sys.stderr, 'result graph:'
print >>sys.stderr, generate_graph(res)
print >>sys.stderr, 'expected graph:'
print >>sys.stderr, generate_graph(out)
if fail:
raise
def graph(parser, *exp, **kwargs): def graph(parser, *exp, **kwargs):
return generate_graph(ParserWrapper(parser, **kwargs).run(exp)) return generate_graph(ParserWrapper(parser, **kwargs).run(exp))
......
import unittest import unittest
from src.parser import Parser from src.parser import Parser
from src.node import ExpressionNode as N, ExpressionLeaf as L from src.node import ExpressionLeaf as L
from tests.parser import run_expressions from tests.parser import run_expressions, apply_expressions
class TestB1Ch08(unittest.TestCase): class TestB1Ch08(unittest.TestCase):
def test_diagnostic_test(self): def test_diagnostic_test_parser(self):
run_expressions(Parser, [ run_expressions(Parser, [
('6*5^2', N('*', L(6), N('^', L(5), L(2)))), ('6*5^2', L(6) * L(5) ** 2),
('-5*(-3)^2', N('*', N('-', L(5)), ('-5*(-3)^2', (-L(5)) * (-L(3)) ** 2),
N('^', N('-', L(3)), L(2)))), ('7p-3p', L(7) * 'p' + -(L(3) * 'p')),
('-5*(-3)^2', N('*', N('-', L(5)), ('-5a*-6', (-L(5)) * 'a' * (-L(6))),
N('^', N('-', L(3)), L(2)))), ('3a-8--5-2a', L(3) * 'a' + -L(8) + -(-L(5)) + -(L(2) * 'a')),
('7p-3p', N('-', N('*', L(7), L('p')), N('*', L(3), L('p')))), ])
('-5a*-6', N('*', N('*', N('-', L(5)), L('a')),
N('-', L(6)))), def test_diagnostic_test_application(self):
('3a-8--5-2a', N('-', N('-', N('-', N('*', L(3), L('a')), L(8)), apply_expressions(Parser, [
N('-', L(5))), N('*', L(2), L('a')))), ('7p+2p', 1, (L(7) + 2) * 'p'),
#('7p-3p', 1, (L(7) - 3) * 'p'),
]) ])
...@@ -9,21 +9,12 @@ class TestB1Ch10(unittest.TestCase): ...@@ -9,21 +9,12 @@ class TestB1Ch10(unittest.TestCase):
def test_diagnostic_test(self): def test_diagnostic_test(self):
run_expressions(Parser, [ run_expressions(Parser, [
('5(a-2b)', N('*', L(5), N('-', L('a'), ('5(a-2b)', L(5) * (L('a') + -(L(2) * 'b'))),
N('*', L(2), L('b'))))), ('-(3a+6b)', -(L(3) * L('a') + L(6) * 'b')),
('-(3a+6b)', N('-', N('+', N('*', L(3), L('a')), ('18-(a-12)', L(18) + -(L('a') + -L(12))),
N('*', L(6), L('b'))))),
('18-(a-12)', N('-', L(18),
N('-', L('a'), L(12)))),
('-p-q+5(p-q)-3q-2(p-q)', ('-p-q+5(p-q)-3q-2(p-q)',
N('-', -L('p') + -L('q') + L(5) * (L('p') + -L('q')) + -(L(3) * 'q') \
N('-', + - (L(2) * (L('p') + -L('q')))
N('+', N('-', N('-', L('p')), L('q')),
N('*', L(5), N('-', L('p'), L('q')))),
N('*', L(3), L('q'))
),
N('*', L(2), N('-', L('p'), L('q')))
)
), ),
('(2+3/7)^4', ('(2+3/7)^4',
N('^', N('+', L(2), N('/', L(3), L(7))), L(4)) N('^', N('+', L(2), N('/', L(3), L(7))), L(4))
......
...@@ -13,10 +13,10 @@ class TestCalc(unittest.TestCase): ...@@ -13,10 +13,10 @@ class TestCalc(unittest.TestCase):
def test_basic_on_exp(self): def test_basic_on_exp(self):
expressions = [('4', L(4)), expressions = [('4', L(4)),
('3+4', N('+', L(3), L(4))), ('3+4', L(3) + L(4)),
('3-4', N('-', L(3), L(4))), ('3-4', L(3) + -L(4)),
('3/4', N('/', L(3), L(4))), ('3/4', L(3) / L(4)),
('-4', N('-', L(4))), ('-4', -L(4)),
('3^4', N('^', L(3), L(4))), ('3^4', N('^', L(3), L(4))),
('(2)', L(2))] ('(2)', L(2))]
...@@ -83,7 +83,7 @@ class TestCalc(unittest.TestCase): ...@@ -83,7 +83,7 @@ class TestCalc(unittest.TestCase):
def test_negation(self): def test_negation(self):
run_expressions(Parser, [ run_expressions(Parser, [
('-9', N('-', L(9))), ('-9', -L(9)),
('--9', N('-', N('-', L(9)))), ('--9', --L(9)),
('a--9', N('-', L('a'), N('-', L(9)))), ('a--9', L('a') + -(-L(9))),
]) ])
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment