Interpreter Design Pattern in Visual Basic .NET

Last Updated: September 9, 2017

Definition

Given a language, define a representation for its grammar along with an interpreter that uses the representation to interpret sentences in the language.

This is about creating interpreter for a language which can be new language or existing one. To use the Interpreter Design Pattern effectively one should have good knowledge about computer language grammar.

We will see the UML diagram for the Interpreter Design Pattern

Participant

Classes and objects you find in Interpreter Design Pattern
Context
Global information of the Interpreter is kept here
Client

  • Client defines the object tree which represent the language with grammar. Syntax tree is built using instances of the NonterminalExpression and TerminalExpression classes
  • Invokes the Interpret operation.

Expression
Defines Interpret method used by Terminal and NonTerminal expressions
TerminalExpression
Implements an Interpret operation
NonTerminalExpression
Implements an Interpret operation

Interpreter Design Pattern Example in VB.NET

In this tutorial I will implement the Reverse Polish Notation (RPN) or Postfix notation. It is a mathematical notation in which operators follow their operands
Postfix expression can be written as 1 2 4 + – which is equivalent to (1+2-4)

First we will draw the UML diagram for our program

This is the algorithm for evaluating the postfix expression using stack

for each token in the postfix expression:
if token is an operator:
operand_1 ← pop from the stack
operand_2 ← pop from the stack
result ← evaluate token with operand_1 and operand_2
push result back onto the stack
else if token is an operand:
push token onto the stack
result ← pop from the stack

IExpression Interface

Public Interface IExpression
    Function Interpret() As Integer
End Interface

Add NonTerminal Expression Class

Public Class Add
    Implements IExpression

    Dim LHE As IExpression
    Dim RHE As IExpression
    Sub New(ByVal LHE As IExpression, ByVal RHE As IExpression)
        Me.LHE = LHE
        Me.RHE = RHE
    End Sub
    Public Function Interpret() As Integer Implements IExpression.Interpret
        Return LHE.Interpret() + RHE.Interpret()
    End Function
End Class

Substract NonTerminal Expression Class

Public Class Substract

    Implements IExpression
    'Left Hand Expression
    Dim LHE As IExpression
    'Right Hand Expression
    Dim RHE As IExpression
    Sub New(ByVal LHE As IExpression, ByVal RHE As IExpression)
        Me.LHE = LHE
        Me.RHE = RHE
    End Sub

    Public Function Interpret() As Integer Implements IExpression.Interpret
        Return LHE.Interpret() - RHE.Interpret()
    End Function
End Class


Multiply NonTerminal Expression Class

Public Class Multiply

    Implements IExpression
    'Left Hand Expression
    Dim LHE As IExpression
    'Right Hand Expression
    Dim RHE As IExpression
    Sub New(ByVal LHE As IExpression, ByVal RHE As IExpression)
        Me.LHE = LHE
        Me.RHE = RHE
    End Sub

    Public Function Interpret() As Integer Implements IExpression.Interpret
        Return LHE.Interpret() * RHE.Interpret()
    End Function
End Class


Number Terminal Class

Public Class Number
    Implements IExpression

    Dim n As Integer
    Sub New(ByVal n As Integer)
        Me.n = n
    End Sub

    Public Function Interpret() As Integer Implements IExpression.Interpret
        Return n
    End Function
End Class

This is the client part of the above patter. We can use client to run the program

Module Module1

    Sub Main()
        Dim token As String = "7 3 - 2 1 + *"
        Dim mStatck As New Stack(Of IExpression)
        Dim LHE As IExpression
        Dim RHE As IExpression
        Dim strArray() As String = token.Split(" ")
        For Each str As String In strArray
            If (str.Equals("+") Or (str.Equals("-")) Or (str.Equals("*"))) Then
                RHE = mStatck.Pop()
                LHE = mStatck.Pop()

                If (str.Equals("+")) Then
                    mStatck.Push(New Add(LHE, RHE))
                End If

                If (str.Equals("-")) Then
                    mStatck.Push(New Substract(LHE, RHE))
                End If

                If (str.Equals("*")) Then
                    mStatck.Push(New Multiply(LHE, RHE))
                End If
            Else
                mStatck.Push(New Number(str))

            End If


        Next
        Console.WriteLine(token + " is equal to :" + mStatck.Pop().Interpret().ToString())
        Console.ReadLine()

    End Sub

End Module

Finally you will see the following output

7 3 - 2 1 + * is equal to :12