class Lisp::Primitive
Attributes
doc[R]
name[R]
Public Class Methods
new(name, arity, doc, special, &implementation)
click to toggle source
# File lib/rubylisp/primitive.rb, line 14 def initialize(name, arity, doc, special, &implementation) @name = name @arity = arity @doc = doc @special = special @implementation = implementation end
register(name, arity, doc="", special=false, env=Lisp::EnvironmentFrame.global, &implementation)
click to toggle source
# File lib/rubylisp/primitive.rb, line 8 def self.register(name, arity, doc="", special=false, env=Lisp::EnvironmentFrame.global, &implementation) instance = self.new(name, arity, doc, special, &implementation) env.bind(Symbol.named(name), instance) end
Public Instance Methods
apply_to(args, env)
click to toggle source
# File lib/rubylisp/primitive.rb, line 43 def apply_to(args, env) return Lisp::Debug.process_error("Wrong number of arguments to #{@name}. Expected #{@arity} but got #{args.length}.", env) unless check_arity(args) cooked_args = if @special args else Lisp::ConsCell.array_to_list(args.to_a.map {|i| i.evaluate(env)}) end @implementation.call(cooked_args, env) end
apply_to_without_evaluating(args, env)
click to toggle source
# File lib/rubylisp/primitive.rb, line 55 def apply_to_without_evaluating(args, env) return Lisp::Debug.process_error("Wrong number of arguments to #{@name}. Expected #{@arity} but got #{args.length}.", env) unless check_arity(args) @implementation.call(args, env) end
check_arity(args)
click to toggle source
# File lib/rubylisp/primitive.rb, line 23 def check_arity(args) return true if @arity == "*" number_of_args = args.length @arity.split("|").map do |term| m = /^(\d+)$/.match(term) return true if m && number_of_args == m[1].to_i m = /^>=(\d+)$/.match(term) return true if m && number_of_args >= m[1].to_i m = /^\((\d+),(\d+)\)$/.match(term) return true if m && number_of_args >= m[1].to_i && number_of_args <= m[2].to_i end false end
primitive?()
click to toggle source
# File lib/rubylisp/primitive.rb, line 70 def primitive? true end
special?()
click to toggle source
# File lib/rubylisp/primitive.rb, line 75 def special? @special end
to_s()
click to toggle source
# File lib/rubylisp/primitive.rb, line 61 def to_s if @special "<specialform: #{@name}>" else "<primitive: #{@name}>" end end
type()
click to toggle source
# File lib/rubylisp/primitive.rb, line 80 def type if @special :specialform else :primitive end end