A Second Visitor, No Node Changes

Step 4: A Second Visitor, No Node Changes

Here is the payoff of the pattern. To add a brand new operation, you write a new visitor. You do NOT touch Num, Add, or Mul at all.

PrintVisitor renders the tree as a fully parenthesized string:

  • visit_num(node) returns str(node.value)
  • visit_add(node) returns "(" + left + " + " + right + ")"
  • visit_mul(node) returns "(" + left + " * " + right + ")"

where left is node.left.accept(self) and right is node.right.accept(self). One new class, zero changes to the nodes.

Hints
Starter code
class Num:
    def __init__(self, value):
        self.value = value

    def accept(self, visitor):
        return visitor.visit_num(self)


class Add:
    def __init__(self, left, right):
        self.left = left
        self.right = right

    def accept(self, visitor):
        return visitor.visit_add(self)


class Mul:
    def __init__(self, left, right):
        self.left = left
        self.right = right

    def accept(self, visitor):
        return visitor.visit_mul(self)


class EvalVisitor:
    def visit_num(self, node):
        return node.value

    def visit_add(self, node):
        return node.left.accept(self) + node.right.accept(self)

    def visit_mul(self, node):
        return node.left.accept(self) * node.right.accept(self)


class PrintVisitor:
    def visit_num(self, node):
        """Return the value of a Num node as a string."""
        # TODO: return str(node.value)
        pass

    def visit_add(self, node):
        """Return a fully parenthesized sum string."""
        # TODO: return "(" + node.left.accept(self) + " + " + node.right.accept(self) + ")"
        pass

    def visit_mul(self, node):
        """Return a fully parenthesized product string."""
        # TODO: return "(" + node.left.accept(self) + " * " + node.right.accept(self) + ")"
        pass
Write it on a laptop

The editor and the test runner need a wide screen. Open this page on a desktop browser and your progress will be waiting.