I have been spending some time over at codewars.com. It is an interactive platform where you can train on Javascript, Coffeescript, or Ruby exercises. The other participants in the site add their own exercises.
I just added an exercise to implement Lisp-style Generic Functions (including the standard method combinations) in Javascript. I’m pretty happy with the way my code came out.
var append = defgeneric('append');
append.defmethod('Array,Array', function (a,b) { return a.concat(b); });
append.defmethod('*,Array', function (a,b) { return [a].concat(b); });
append.defmethod('Array,*', function (a,b) { return a.concat([b]); });
append([1,2],[3,4]); // => [1,2,3,4]
append(1,[2,3,4]); // => [1,2,3,4]
append([1,2,3],4); // => [1,2,3,4]
append(1,2,3,4); // => throws "No method found for append with args: number,number,number,number
append.defmethod('Array,Array', function (a,b) { return a.concat(b); });
append.defmethod('*,Array', function (a,b) { return [a].concat(b); });
append.defmethod('Array,*', function (a,b) { return a.concat([b]); });
append([1,2],[3,4]); // => [1,2,3,4]
append(1,[2,3,4]); // => [1,2,3,4]
append([1,2,3],4); // => [1,2,3,4]
append(1,2,3,4); // => throws "No method found for append with args: number,number,number,number
Here’s a link directly to the exercise, but if you register for the site with this link, I get bonus points.
http://github.com/sykopomp/genfun.js 🙂
You rule. That’s awesome. I suppose I should have done a literature search first. 🙂
I like your use of an array of prototypes where I used a string for the discriminator. I like my defmethod being a method on the generic function better than having it be a stand-alone function which takes a generic as an argument. *shrug*
ps: I corrected your URL, you left the .js off of it.
I really like that defgeneric interface. It’s clever.
I made the defgeneric() and the defmethod() both return the generic so that you can chain them together with method chaining, too.
addMethod used to be a method of the generic function objects, but I changed it because I thought I should walk the walk. 🙂
I’ve done a similar thing in the past, too.
https://github.com/ympbyc/js-clos
Looks pretty similar to Jsh’s genfun.