type check and curry

Run Settings
LanguageRuby
Language Version
Run Command
def mydef(n, **k, &b) raise LocalJumpError, 'no block given' unless block_given? raise ArgumentError, 'arity not matched' unless b.arity == k.size define_singleton_method n do |*xs| a, ts = [], k.values c = -> x do x.is_a?(t = ts.shift)?(a << x):(raise TypeError, "expect #{t}, got #{x}") ts.empty? ? b.(*a) : c end xs.inject(c) { |r, x| r = r.(x) } end end mydef(:add, a: Integer, b: Integer) { |a, b| a + b } p add(3, 5) p add(3).(5) p add.(3).(5) # add(0.1, 0.2) module T @@__t = { :' reserved types ' => [] } def typed(*ts) @@__t[:' reserved types '] = ts end def method_added(name) unless @@__t.include?(name) @@__t[name] = @@__t[:' reserved types '] return if @@__t[name].empty? @@__t[:' reserved types '] = [] old = instance_method(name) define_method name do |*xs| a, ts, b = [], @@__t[name].clone, old.bind(self) c = -> x do if x.is_a?(t = ts.shift) a << x else raise TypeError, "expect #{t}, got #{x.inspect}" end ts.empty? ? b.(*a) : c end xs.inject(c) { |r, x| r = r.(x) } end end end end class A extend T def add a, b a + b end typed Integer, Integer def mul a, b a * b end end a = A.new p a.add(3, 5) p a.add('3', '5') p a.mul(3, 5) # a.mul('3', 5)
Editor Settings
Theme
Key bindings
Full width
Lines