Skip to content

Commit

Permalink
Fixes #474 -- add _.partial
Browse files Browse the repository at this point in the history
  • Loading branch information
jashkenas committed Jan 30, 2013
1 parent ce3d1ae commit 789da94
Show file tree
Hide file tree
Showing 2 changed files with 21 additions and 5 deletions.
12 changes: 10 additions & 2 deletions test/functions.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,10 @@ $(document).ready(function() {
func = _.bind(func, this, 'hello');
equal(func('moe'), 'hello: moe', 'the function was partially applied in advance');

var func = _.bind(func, this, 'curly');
func = _.bind(func, this, 'curly');
equal(func(), 'hello: curly', 'the function was completely applied in advance');

var func = function(salutation, firstname, lastname) { return salutation + ': ' + firstname + ' ' + lastname; };
func = function(salutation, firstname, lastname) { return salutation + ': ' + firstname + ' ' + lastname; };
func = _.bind(func, this, 'hello', 'moe', 'curly');
equal(func(), 'hello: moe curly', 'the function was partially applied in advance and can accept multiple arguments');

Expand All @@ -37,6 +37,14 @@ $(document).ready(function() {
equal(Boundf().hello, "moe curly", "When called without the new operator, it's OK to be bound to the context");
});

test("partial", function() {
var obj = {name: 'moe'};
var func = function() { return this.name + ' ' + _.toArray(arguments).join(' '); };

obj.func = _.partial(func, 'a', 'b');
equal(obj.func('c', 'd'), 'moe a b c d', 'can partially apply');
});

test("bindAll", function() {
var curly = {name : 'curly'}, moe = {
name : 'moe',
Expand Down
14 changes: 11 additions & 3 deletions underscore.js
Original file line number Diff line number Diff line change
Expand Up @@ -578,9 +578,8 @@
var ctor = function(){};

// Create a function bound to a given object (assigning `this`, and arguments,
// optionally). Binding with arguments is also known as `curry`.
// Delegates to **ECMAScript 5**'s native `Function.bind` if available.
// We check for `func.bind` first, to fail fast when `func` is undefined.
// optionally). Delegates to **ECMAScript 5**'s native `Function.bind` if
// available.
_.bind = function(func, context) {
if (func.bind === nativeBind && nativeBind) return nativeBind.apply(func, slice.call(arguments, 1));
var args = slice.call(arguments, 2);
Expand All @@ -589,6 +588,15 @@
};
};

// Partially apply a function by creating a version that has had some of its
// arguments pre-filled, without changing its dynamic `this` context.
_.partial = function(func) {
var args = slice.call(arguments, 1);
return function() {
return func.apply(this, args.concat(slice.call(arguments)));
};
};

// Bind all of an object's methods to that object. Useful for ensuring that
// all callbacks defined on an object belong to it.
_.bindAll = function(obj) {
Expand Down

0 comments on commit 789da94

Please sign in to comment.