class SXP::Reader::CommonLisp
A Common Lisp S-expressions parser.
Constants
- CHARACTERS
Escape characters, used in the form `#Backspace`. Case is treated insensitively @see www.cs.cmu.edu/Groups/AI/html/cltl/clm/node22.html
- DECIMAL
- INTEGER_BASE_10
- INTEGER_BASE_16
- INTEGER_BASE_2
- INTEGER_BASE_8
- OPTIONS
- RATIONAL
Public Class Methods
Initializes the reader.
@param [IO, StringIO, String] input @param [Hash{Symbol => Object}] options @option options [Object] :nil (nil) @option options [Object] :t (true) @option options [Object] :quote (:quote) @option options [Object] :function (:function)
SXP::Reader::new
# File lib/sxp/reader/common_lisp.rb, line 39 def initialize(input, **options, &block) super(input, **OPTIONS.merge(options), &block) end
Public Instance Methods
Read characters sequences like `#backspace`. Otherwise, reads a single character. Requires the ability to put eroneously read characters back in the input stream
@return [String] @see www.cs.cmu.edu/Groups/AI/html/cltl/clm/node22.html
# File lib/sxp/reader/common_lisp.rb, line 117 def read_character lit = read_literal return " " if lit.empty? && peek_char == " " CHARACTERS.fetch(lit.downcase) do |string| # Return just the first character unread(string[1..-1]) string[0,1] end end
Reads `#'mapcar` forms.
@return [Array]
# File lib/sxp/reader/common_lisp.rb, line 106 def read_function [options[:function] || :function, read] end
Reads `'foobar` forms.
@return [Array]
# File lib/sxp/reader/common_lisp.rb, line 97 def read_quote skip_char # "'" [options[:quote] || :quote, read] end
@return [Object]
# File lib/sxp/reader/common_lisp.rb, line 56 def read_sharp skip_char # '#' case char = read_char when ?b, ?B then read_integer(2) when ?o, ?O then read_integer(8) when ?x, ?X then read_integer(16) when ?\\ then read_character when ?( then read_vector when ?' then read_function else raise Error, "invalid sharp-sign read syntax: ##{char.chr}" end end
@return [Symbol]
# File lib/sxp/reader/common_lisp.rb, line 71 def read_symbol(delimiter = nil) buffer = String.new skip_char # '|' until delimiter === peek_char buffer << case char = read_char when ?\\ then read_character else char end end skip_char # '|' buffer.to_sym end
@return [Object]
SXP::Reader::Basic#read_token
# File lib/sxp/reader/common_lisp.rb, line 45 def read_token case peek_char when ?# then [:atom, read_sharp] when ?| then [:atom, read_symbol(?|)] when ?' then [:atom, read_quote] else super end end
Reads `#(1 2 3)` forms.
@return [Array]
# File lib/sxp/reader/common_lisp.rb, line 89 def read_vector raise NotImplementedError, "#{self.class}#read_vector" # TODO end
@return [void]
# File lib/sxp/reader/common_lisp.rb, line 130 def skip_comments until eof? case (char = peek_char).chr when /\s+/ then skip_char when /;/ then skip_line else break end end end