```Issue #12854 has been updated by Chad Brewbaker.

Defining complex functions with curry would be nontrivial:

~~~ ruby
double = ->(a)(a+a)
g = ->(a,b,c){ f.call(1,c, double.call(a))}
~~~

I suggest adding Proc#trans and Proc#lens.

Proc#trans applies a transformation (repeated permutation) to the argument list.

Proc#lens is list of functions applied to the argument list. Think of a constant as a function that takes zero arguments.

~~~ ruby
class Proc
def trans(*args)
->(*a){
a.flatten!
bound = [a.size, args.size].min
alist = (0...bound).collect{|i| a[args[i] ] }
self.call(alist)
}
end

def lens(*args)
concretes = [Integer,TrueClass,FalseClass,String,Float,Symbol,Array,Hash]
->(*a){
a.flatten!
bound = [a.size, args.size].min
alist = (0...bound).collect{|i|
if(concretes.include?(args[i].class))
args[i]
else
args[i].call(a[i])
end
}
self.call(alist)
}
end
end

id = ->(*args){args.inspect}

f = id.trans(0,1,2)
p f.call(0,1,2) == "[[0, 1, 2]]"

g = id.trans(2,0,0)
p g.call() == "[[]]"
p g.call(0)  == "[[nil]]"
p g.call(0,1) == "[[nil, 0]]"
p g.call(0,1,2) == "[[2, 0, 0]]"
p g.call(0,1,2,3,4) == "[[2, 0, 0]]"

single = ->(a){a}
double = ->(a){a+a}
triple = ->(a){a+a+a}
q = id.lens(single, double,triple)
p q.call(5,5,5) == "[[5, 10, 15]]"
p q.call(1,2,3) == "[[1, 4, 9]]"

h = q.lens(single,double,triple)
p h.call(5,5,5) == "[[5, 20, 45]]"
k = id.lens(single, 444,triple)
p k.call(4,4,4,4,4) == "[[4, 444, 12]]"
~~~

----------------------------------------
Feature #12854: Proc#curry should return an instance of the class, not Proc
https://bugs.ruby-lang.org/issues/12854#change-62439

* Author: Ryan Davis
* Status: Feedback
* Priority: Normal
* Assignee:
* Target version:
----------------------------------------
~~~ ruby
class ChainedProc < Proc
end

ChainedProc.new { |x, y, z| 42 }.curry.class # => Proc
~~~

--
https://bugs.ruby-lang.org/

Unsubscribe: <mailto:ruby-core-request / ruby-lang.org?subject=unsubscribe>
<http://lists.ruby-lang.org/cgi-bin/mailman/options/ruby-core>
```