Class: BCDice::Command::Lexer

Inherits:
Object
  • Object
show all
Defined in:
lib/bcdice/command/lexer.rb

Constant Summary collapse

SYMBOLS =
{
  "+" => :PLUS,
  "-" => :MINUS,
  "*" => :ASTERISK,
  "/" => :SLASH,
  "(" => :PARENL,
  ")" => :PARENR,
  "?" => :QUESTION,
  "@" => :AT,
  "#" => :SHARP,
  "$" => :DOLLAR,
}.freeze

Instance Method Summary collapse

Constructor Details

#initialize(source, notations) ⇒ Lexer

Returns a new instance of Lexer.



22
23
24
25
26
27
28
29
# File 'lib/bcdice/command/lexer.rb', line 22

def initialize(source, notations)
  # sourceが空文字だとString#splitが空になる
  source = source&.split(" ", 2)&.first || ""
  @scanner = StringScanner.new(source)
  @notations = notations.map do |n|
    n.is_a?(String) ? Regexp.new(n) : n
  end
end

Instance Method Details

#next_tokenObject



31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
# File 'lib/bcdice/command/lexer.rb', line 31

def next_token
  return [false, "$"] if @scanner.eos?

  @notations.each do |n|
    token = @scanner.scan(n)
    return [:NOTATION, token] if token
  end

  if (number = @scanner.scan(/\d+/))
    [:NUMBER, number.to_i]
  elsif (cmp_op = @scanner.scan(/[<>!=]+/))
    cmp_op = Normalize.comparison_operator(cmp_op)
    type = cmp_op ? :CMP_OP : :ILLEGAL
    [type, cmp_op]
  else
    char = @scanner.getch.upcase
    type = SYMBOLS[char] || char.to_sym
    [type, char]
  end
end

#sourceObject



52
53
54
# File 'lib/bcdice/command/lexer.rb', line 52

def source
  @scanner.string
end