Advertisement
Guest User

Mun pyyttoni

a guest
Oct 15th, 2019
86
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 3.96 KB | None | 0 0
  1. import re
  2. '''
  3. Start by familiarizing yourself with the classes ``ExpressionTree`` and
  4. ``ETNode``, which are included in the exercise package.
  5. ``ExpressionTree`` is a binary tree which can be used to convert
  6. postfix expressions into infix format. The conversion takes place by first
  7. building a binary tree from the operators and operands of the postfix
  8. exression. After the tree is complete, the infix version of the original
  9. expression can be obtained by traversing the nodes of the tree using an
  10. inorder traversal.
  11.  
  12. The class ``ExpressionTree`` is almost ready, but it lacks the method
  13. used to traverse the nodes in correct order. Your task is to implement the
  14. required functionality into the method ``_visit_inorder`` so that it
  15. returns a list of the values of the tree nodes
  16. in inorder. Remember also to add parentheses at correct positions.
  17. Even though the parentheses would be trivial, for example ``((1*2)+3)``,
  18. they should still be added for every operator. This is of course a bit
  19. redundant, but it simplifies the task.
  20.  
  21. '''
  22. class ETNode:
  23. """
  24. Simple binary tree node with a value and both left and right pointers.
  25. """
  26. def __init__(self, value):
  27. self.value = value
  28. self.left = None
  29. self.right = None
  30.  
  31. def __str__(self):
  32. return str(self.value)
  33.  
  34.  
  35. class ExpressionTree:
  36. """
  37. Simple binary expression tree capable of parsing postfix expressions
  38. and returning infix expressions.
  39. """
  40. # Supported operators
  41. OPERATORS = {'+', '-', '*', '/'}
  42.  
  43. def __init__(self):
  44. self.root = None
  45. self._stack = list()
  46.  
  47.  
  48. def construct_from_postfix(self, expression):
  49. """Construct the expression tree by parsing the given expression string."""
  50. if not expression:
  51. return
  52.  
  53. # Iterate over the string 'expression' inserting elements into the tree,
  54. # while skipping spaces
  55. operators = re.escape(''.join(self.OPERATORS))
  56. pattern = r"\w+|[{}]".format(operators)
  57. for match in re.finditer(pattern, expression):
  58. element = match.group(0)
  59. self._insert(element)
  60.  
  61. if not self._stack:
  62. raise RuntimeError("There is no root operator after inserting {!r} into the tree.".format(expression))
  63.  
  64. # Set the last operator as the root
  65. self.root = self._stack.pop()
  66.  
  67. if self._stack:
  68. raise RuntimeError("The expression stack should be empty after evaluating all characters from the expression: {!r}.".format(expression))
  69.  
  70.  
  71. def _insert(self, value):
  72. """Insert operand or operator 'value' into this tree."""
  73. if value not in self.OPERATORS:
  74. # value is an operand
  75. self._stack.append(ETNode(value))
  76. return
  77.  
  78. if not self._stack:
  79. # value is an operator but there's nothing in the stack to operate on
  80. raise RuntimeError("Cannot add operator {!r}, the expression stack is empty.".format(value))
  81.  
  82. # Merge subtrees from stack with operator as their new root
  83. operator = ETNode(value)
  84. operator.right = self._stack.pop()
  85. operator.left = self._stack.pop()
  86. self._stack.append(operator)
  87.  
  88.  
  89. def as_infix(self):
  90. """Return the infix representation of the current tree as a string."""
  91. return ''.join(map(str, self._visit_inorder()))
  92.  
  93.  
  94. # Write your solution below, there's no need to change anything
  95. # outside this method to get full points.
  96. def _visit_inorder(self, starting_node=None):
  97. """Return a list containing the values of the visited nodes while adding parentheses to retain operator precedence."""
  98. if starting_node is None:
  99. starting_node = self.root
  100.  
  101. raise NotImplementedError("Method _visit_inorder has not yet been implemented.")
  102.  
  103. def inorder(node):
  104. pass
  105.  
  106. inorder(starting_node)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement