Class: Walrus::Grammar::ParserState
- Inherits:
-
Object
- Object
- Walrus::Grammar::ParserState
- Defined in:
- lib/walrus/grammar/parser_state.rb
Overview
Simple class for maintaining state during a parse operation.
Instance Attribute Summary collapse
-
#options ⇒ Object
readonly
Returns the value of attribute options.
-
#remainder ⇒ Object
readonly
Returns the remainder (the unparsed portion) of the string.
Instance Method Summary collapse
-
#auto_skipped(substring) ⇒ Object
The skipped method is used to inform the receiver of a successful parsing event where the parsed substring should be consumed but not included in the accumulated results and furthermore the parse event should not effect the overall bounds of the parse result.
-
#initialize(string, options = {}) ⇒ ParserState
constructor
Raises an ArgumentError if string is nil.
-
#length ⇒ Object
Returns the number of results accumulated so far.
-
#parsed(substring) ⇒ Object
The parsed method is used to inform the receiver of a successful parsing event.
-
#results ⇒ Object
Returns the results accumulated so far.
-
#skipped(substring) ⇒ Object
The skipped method is used to inform the receiver of a successful parsing event where the parsed substring should be consumed but not included in the accumulated results.
Constructor Details
#initialize(string, options = {}) ⇒ ParserState
Raises an ArgumentError if string is nil.
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 |
# File 'lib/walrus/grammar/parser_state.rb', line 29 def initialize(string, = {}) raise ArgumentError if string.nil? self.base_string = string @results = ArrayResult.new # for accumulating results @remainder = @base_string.clone @scanned = '' @options = .clone # start wherever we last finished (doesn't seem to behave different to the alternative) @options[:line_start] = (@options[:line_end] or @options[:line_start] or 0) @options[:column_start] = (@options[:column_end] or @options[:column_start] or 0) # @options[:line_start] = 0 if @options[:line_start].nil? # @options[:column_start] = 0 if @options[:column_start].nil? @options[:line_end] = @options[:line_start] # before parsing begins, end point is equal to start point @options[:column_end] = @options[:column_start] @original_line_start = @options[:line_start] @original_column_start = @options[:column_start] end |
Instance Attribute Details
#options ⇒ Object (readonly)
Returns the value of attribute options.
23 24 25 |
# File 'lib/walrus/grammar/parser_state.rb', line 23 def @options end |
#remainder ⇒ Object (readonly)
Returns the remainder (the unparsed portion) of the string. Will return an empty string if already at the end of the string.
26 27 28 |
# File 'lib/walrus/grammar/parser_state.rb', line 26 def remainder @remainder end |
Instance Method Details
#auto_skipped(substring) ⇒ Object
The skipped method is used to inform the receiver of a successful parsing event where the parsed substring should be consumed but not included in the accumulated results and furthermore the parse event should not effect the overall bounds of the parse result. In reality this means that the method is only ever called upon the successful use of a automatic intertoken “skipping” parslet. By definition this method should only be called for intertoken skipping otherwise incorrect results will be produced.
68 69 70 71 72 73 74 |
# File 'lib/walrus/grammar/parser_state.rb', line 68 def auto_skipped(substring) raise ArgumentError if substring.nil? a, b, c, d = @options[:line_start], @options[:column_start], @options[:line_end], @options[:column_end] # save remainder = update_and_return_remainder_for_string(substring) @options[:line_start], @options[:column_start], @options[:line_end], @options[:column_end] = a, b, c, d # restore remainder end |
#length ⇒ Object
Returns the number of results accumulated so far.
117 118 119 |
# File 'lib/walrus/grammar/parser_state.rb', line 117 def length @results.length end |
#parsed(substring) ⇒ Object
The parsed method is used to inform the receiver of a successful parsing event. Note that substring need not actually be a String but it must respond to the following messages:
- "line_end" and "column_end" so that the end position of the receiver can be updated
As a convenience returns the remainder. Raises an ArgumentError if substring is nil.
54 55 56 57 |
# File 'lib/walrus/grammar/parser_state.rb', line 54 def parsed(substring) raise ArgumentError if substring.nil? update_and_return_remainder_for_string(substring, true) end |
#results ⇒ Object
Returns the results accumulated so far. Returns an empty array if no results have been accumulated. Returns a single object if only one result has been accumulated. Returns an array of objects if multiple results have been accumulated.
80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 |
# File 'lib/walrus/grammar/parser_state.rb', line 80 def results updated_start = [@original_line_start, @original_column_start] updated_end = [@options[:line_end], @options[:column_end]] updated_source_text = @scanned.clone if @results.length == 1 # he we ask the single result to exhibit container-like properties # use the "outer" variants so as to not overwrite any data internal to the result itself # this can happen where a lone result is surrounded only by skipped elements # the result has to convey data about its own limits, plus those of the context just around it results = @results[0] results.outer_start = updated_start if results.start != updated_start results.outer_end = updated_end if results.end != updated_end results.outer_source_text = updated_source_text if results.source_text != updated_source_text # the above trick fixes some of the location tracking issues but opens up another can of worms # uncomment this line to see #return results # need some way of handling unwrapped results (raw results, not AST nodes) as well results.start = updated_start results.end = updated_end results.source_text = updated_source_text else results = @results results.start = updated_start results.end = updated_end results.source_text = updated_source_text end results end |
#skipped(substring) ⇒ Object
The skipped method is used to inform the receiver of a successful parsing event where the parsed substring should be consumed but not included in the accumulated results. The substring should respond to “line_end” and “column_end”. In all other respects this method behaves exactly like the parsed method.
62 63 64 65 |
# File 'lib/walrus/grammar/parser_state.rb', line 62 def skipped(substring) raise ArgumentError if substring.nil? update_and_return_remainder_for_string(substring) end |