Task

Implement a    HQ9+    interpreter or compiler.




# HQ9+ interpreter
 
# execute an HQ9+ program in the code string - code is not case sensitive
hq9 := proc( code :: string ) is
    local hq9Accumulator := 0; # the HQ9+ accumulator
    local hq9Operations  :=    # table of HQ9+ operations and their implemntations
          [ "q" ~ proc() is print( code ) end
          , "h" ~ proc() is print( "Hello, world!" ) end
          , "9" ~ proc() is
                      local writeBottles := proc( bottleCount :: number, message :: string ) is
                                                print( bottleCount
                                                     & " bottle"
                                                     & if bottleCount <> 1 then "s " else " " fi
                                                     & message
                                                     )
                                            end;
 
                      for bottles from 99 to 1 by -1 do
                          writeBottles( bottles, "of beer on the wall" );
                          writeBottles( bottles, "of beer" );
                          print( "Take one down, pass it around," );
                          if bottles > 1 then
                              writeBottles( bottles - 1, "of beer on the wall." )
                          fi;
                          print()
                      od;
                      print( "No more bottles of beer on the wall." )
                  end
          , "+" ~ proc() is inc hq9Accumulator, 1 end
          ];
    for op in lower( code ) do
        if hq9Operations[ op ] <> null then
            hq9Operations[ op ]()
        else
            print( '"' & op & '" not implemented' )
        fi
    od
end;
 
# prompt for HQ9+ code and execute it, repeating until an empty code string is entered
scope
    local code;
    do
        write( "HQ9+> " );
        code := io.read();
        hq9( code )
    until code = ""
epocs;