Class: Alf::Algebra::Signature
- Inherits:
-
Object
- Object
- Alf::Algebra::Signature
- Defined in:
- lib/alf-algebra/alf/algebra/support/signature.rb
Overview
Provides an operator signature
Instance Attribute Summary collapse
-
#arguments ⇒ Array
readonly
Signature arguments.
-
#operator ⇒ Class
readonly
The operator class to which this signature belongs.
-
#options ⇒ Array
readonly
Signature options.
Instance Method Summary collapse
-
#argument(name, domain, default = nil, descr = nil) ⇒ Object
Adds an argument to the signature.
-
#collect_on(op) ⇒ Array
Collects signature values on a given operator.
-
#initialize(operator) {|_self| ... } ⇒ Signature
constructor
Creates an empty signature instance.
-
#install ⇒ Hash
Installs the signature on the operator class.
-
#option(name, domain, default = nil, descr = nil) ⇒ Object
Adds an option to the signature.
-
#option_parser(receiver, opt = OptionParser.new) ⇒ OptionParser
Builds an option parser instance ‘opt` prepared for installing options on `receiver`.
-
#parse_args(args, receiver) ⇒ Operator
Parses arguments ‘args` passed to the operator `initialize` and sets attributes accordingly on `receiver`.
-
#to_lispy ⇒ Object
Returns a lispy synopsis for this signature.
Constructor Details
#initialize(operator) {|_self| ... } ⇒ Signature
Creates an empty signature instance
18 19 20 21 22 23 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 18 def initialize(operator) @operator = operator @arguments = [] = [] yield(self) if block_given? end |
Instance Attribute Details
#arguments ⇒ Array (readonly)
Returns signature arguments.
10 11 12 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 10 def arguments @arguments end |
#operator ⇒ Class (readonly)
Returns the operator class to which this signature belongs.
7 8 9 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 7 def operator @operator end |
#options ⇒ Array (readonly)
Returns signature options.
13 14 15 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 13 def end |
Instance Method Details
#argument(name, domain, default = nil, descr = nil) ⇒ Object
Adds an argument to the signature
30 31 32 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 30 def argument(name, domain, default = nil, descr = nil) arguments << [name, domain, default, descr] end |
#collect_on(op) ⇒ Array
Collects signature values on a given operator.
This methods returns a triple ‘[datasets, arguments, options]` with the respective values collected on `op`.
128 129 130 131 132 133 134 135 136 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 128 def collect_on(op) oper = op.operands args = arguments.map{|name,_| op.send(name) } opts = Hash[.map{|name,dom,defa,_| val = op.send(name) (val == defa) ? nil : [name, val] }.compact] [oper, args, opts] end |
#install ⇒ Hash
Installs the signature on the operator class
This method installs an attr reader and an attr writer for each signature argument and each signature option.
69 70 71 72 73 74 75 76 77 78 79 80 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 69 def install clazz = operator code = (arguments + ).each{|siginfo| name, domain, = siginfo clazz.send(:attr_reader, name) clazz.send(:define_method, :"#{name}=") do |val| instance_variable_set(:"@#{name}", Support.coerce(val, domain)) end clazz.send(:private, :"#{name}=") } end |
#option(name, domain, default = nil, descr = nil) ⇒ Object
Adds an option to the signature
39 40 41 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 39 def option(name, domain, default = nil, descr = nil) << [name, domain, default, descr] end |
#option_parser(receiver, opt = OptionParser.new) ⇒ OptionParser
Builds an option parser instance ‘opt` prepared for installing options on `receiver`.
49 50 51 52 53 54 55 56 57 58 59 60 61 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 49 def option_parser(receiver, opt = OptionParser.new) .each do |option| name, dom, defa, descr = option opt.on(option_name(option), descr || "") do |val| if receiver.is_a?(Hash) receiver[name] = val else receiver.send(:"#{name}=", val) end end end opt end |
#parse_args(args, receiver) ⇒ Operator
Parses arguments ‘args` passed to the operator `initialize` and sets attributes accordingly on `receiver`.
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 115 116 117 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 88 def parse_args(args, receiver) # 1) Check and set operands, passed as an array as first argument invalid_args!(args) unless args.first.is_a?(Array) receiver.send(:operands=, args.shift.map{|op| Operand.coerce(op)}) # 2) Extract options if provided optargs = if args.size == (1+arguments.size) # options are passed as last argument invalid_args!(args) unless args.last.is_a?(Hash) optargs = optargs.merge(args.pop) elsif args.size > arguments.size # too many arguments here invalid_args!(args) end # 3) Set options now, including default ones optargs.each_pair do |name,val| receiver.send(:"#{name}=", val) end # 4) Parse other arguments now with_each_arg(args) do |name,dom,value| invalid_args!(args) if value.nil? receiver.send(:"#{name}=", value) end receiver end |
#to_lispy ⇒ Object
Returns a lispy synopsis for this signature
Example:
Alf::Algebra::Project.signature.to_shell
# => "(project operand, attributes:AttrList, {allbut: Boolean})"
144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 |
# File 'lib/alf-algebra/alf/algebra/support/signature.rb', line 144 def to_lispy cmd = operator.rubycase_name oper = operator.nullary? ? "" : (operator.unary? ? "operand" : "left, right") args = arguments.map{|name,dom,_| dom.to_s =~ /::([A-Za-z]+)$/ "#{name}:#{$1}" }.join(", ") args = (args.empty? ? "#{oper}" : "#{oper}, #{args}").strip opts = .map{|name,dom,_| dom.to_s =~ /::([A-Za-z]+)$/ "#{name}: #{$1}" }.join(', ') opts = opts.empty? ? "" : "{#{opts}}" argopt = [args, opts].select{|s| !s.empty?}.join(', ') "(#{cmd} #{argopt}".strip + ")" end |