class KPeg::Grammar

Attributes

directives[R]
foreign_grammars[R]
rule_order[R]
rules[R]
setup_actions[R]
variables[R]

Public Class Methods

new() click to toggle source
# File lib/kpeg/grammar.rb, line 626
def initialize
  @directives = {}
  @rules = {}
  @rule_order = []
  @setup_actions = []
  @foreign_grammars = {}
  @variables = {}
end
resolve(obj) click to toggle source
# File lib/kpeg/grammar.rb, line 680
def self.resolve(obj)
  case obj
  when Operator
    return obj
  when Symbol
    return RuleReference.new(obj.to_s)
  when String
    return LiteralString.new(obj)
  when Array
    ops = []
    obj.each do |x|
      case x
      when Sequence
        ops.concat x.ops
      when Operator
        ops << x
      else
        ops << resolve(x)
      end
    end

    return Sequence.new(*ops)
  when Range
    return CharRange.new(obj.begin.to_s, obj.end.to_s)
  when Regexp
    return LiteralRegexp.new(obj)
  else
    raise "Unknown obj type - #{obj.inspect}"
  end
end

Public Instance Methods

[](rule) click to toggle source

Use these to access the rules unambigiously

# File lib/kpeg/grammar.rb, line 712
def [](rule)
  ref(rule.to_s)
end
[]=(name, rule) click to toggle source
# File lib/kpeg/grammar.rb, line 716
def []=(name, rule)
  set(name, rule)
end
action(action) click to toggle source
# File lib/kpeg/grammar.rb, line 842
def action(action)
  Action.new action
end
add_directive(name, body) click to toggle source
# File lib/kpeg/grammar.rb, line 639
def add_directive(name, body)
  if @directives.include? name
    warn "directive #{name.inspect} appears more than once"
  end

  @directives[name] = body
end
add_foreign_grammar(name, str) click to toggle source
# File lib/kpeg/grammar.rb, line 651
def add_foreign_grammar(name, str)
  @foreign_grammars[name] = str
end
add_setup(act) click to toggle source
# File lib/kpeg/grammar.rb, line 647
def add_setup(act)
  @setup_actions << act
end
andp(node) click to toggle source
# File lib/kpeg/grammar.rb, line 808
def andp(node)
  AndPredicate.new Grammar.resolve(node)
end
any(*nodes, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 765
def any(*nodes, &b)
  nodes.map! { |x| Grammar.resolve(x) }
  op = Choice.new(*nodes)
  op.set_action(b) if b
  op
end
bounds(op) click to toggle source
# File lib/kpeg/grammar.rb, line 850
def bounds(op)
  Bounds.new Grammar.resolve(op)
end
collect(op) click to toggle source
# File lib/kpeg/grammar.rb, line 846
def collect(op)
  Collect.new Grammar.resolve(op)
end
dot(&b) click to toggle source
# File lib/kpeg/grammar.rb, line 741
def dot(&b)
  op = Dot.new
  op.set_action(b) if b
  op
end
find(name) click to toggle source
# File lib/kpeg/grammar.rb, line 676
def find(name)
  @rules[name]
end
foreign_invoke(gram, name, args=nil) click to toggle source

Invoke a rule defined on a foreign grammar

Parameters:

gram

The name of the grammar that the rule will be reference from

name

The name of the rule that will be invoked

args

Any arguements that should be passed to the rule

Returns:

A new ForeignInvokeRule
# File lib/kpeg/grammar.rb, line 834
def foreign_invoke(gram, name, args=nil)
  ForeignInvokeRule.new gram, name.to_s, args
end
invoke(name, args=nil) click to toggle source
# File lib/kpeg/grammar.rb, line 820
def invoke(name, args=nil)
  InvokeRule.new name.to_s, args
end
kleene(node, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 786
def kleene(node, &b)
  multiple Grammar.resolve(node), 0, nil, &b
end
lit(obj, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 735
def lit(obj, &b)
  op = Grammar.resolve(obj)
  op.set_action(b) if b
  op
end
many(node, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 782
def many(node, &b)
  multiple Grammar.resolve(node), 1, nil, &b
end
maybe(node, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 778
def maybe(node, &b)
  multiple Grammar.resolve(node), 0, 1, &b
end
method_missing(meth, *args) click to toggle source
Calls superclass method
# File lib/kpeg/grammar.rb, line 720
def method_missing(meth, *args)
  meth_s = meth.to_s

  if meth_s[-1,1] == "="
    rule = args.first
    set(meth_s[0..-2], rule)
    return rule
  elsif !args.empty?
    super
  end

  # Hm, I guess this is fine. It might end up confusing people though.
  return ref(meth.to_s)
end
multiple(node, min, max, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 772
def multiple(node, min, max, &b)
  op = Multiple.new Grammar.resolve(node), min, max
  op.set_action(b) if b
  op
end
notp(node) click to toggle source
# File lib/kpeg/grammar.rb, line 812
def notp(node)
  NotPredicate.new Grammar.resolve(node)
end
range(start, fin, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 759
def range(start, fin, &b)
  op = CharRange.new(start, fin)
  op.set_action(b) if b
  op
end
ref(name, other_grammar=nil, args=nil) click to toggle source
# File lib/kpeg/grammar.rb, line 816
def ref(name, other_grammar=nil, args=nil)
  RuleReference.new name.to_s, other_grammar, args
end
reg(reg, opts=nil, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 753
def reg(reg, opts=nil, &b)
  op = LiteralRegexp.new reg, opts
  op.set_action(b) if b
  op
end
root() click to toggle source
# File lib/kpeg/grammar.rb, line 659
def root
  @rules["root"]
end
seq(*nodes, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 790
def seq(*nodes, &b)
  ops = []
  nodes.each do |x|
    case x
    when Sequence
      ops.concat x.ops
    when Operator
      ops << x
    else
      ops << Grammar.resolve(x)
    end
  end

  op = Sequence.new(*ops)
  op.set_action(b) if b
  op
end
set(name, op, args=nil) click to toggle source
# File lib/kpeg/grammar.rb, line 663
def set(name, op, args=nil)
  if @rules.key? name
    raise "Already set rule named '#{name}'"
  end

  op = Grammar.resolve(op)

  @rule_order << name

  rule = Rule.new(name, op, args)
  @rules[name] = rule
end
set_variable(name, val) click to toggle source
# File lib/kpeg/grammar.rb, line 655
def set_variable(name, val)
  @variables[name] = val
end
str(str, &b) click to toggle source
# File lib/kpeg/grammar.rb, line 747
def str(str, &b)
  op = LiteralString.new str
  op.set_action(b) if b
  op
end
t(op, name=nil) click to toggle source
# File lib/kpeg/grammar.rb, line 838
def t(op, name=nil)
  Tag.new Grammar.resolve(op), name
end