Javascript: always pass nth argument in functions as fixed default
the function takes 3 parameters of type
function p(x,y,z){
console.log(arguments);
}
so when we call it p (12,21,32)
the fourth argument must pass, as they say 56
so efficiently the call should be p (12,21,32,56)
How to do it?
Condition We cannot change the definition of the function. I need to partially bind the fourth argument as something like
p = p.bind (this, '', '', '', 56); or use lodash
and then call p later like
p (12.21.32);
so 56 should pass by default
source to share
You can use _.partialRight()
to create a new function that adds arguments to the end of the original function:
function p(a, b, c)
{
alert([].join.call(arguments, ','));
}
p = _.partialRight(p, 56);
p(1,2,3); // 1,2,3,56
<script src="https://raw.githubusercontent.com/lodash/lodash/3.9.3/lodash.js"></script>
To precisely specify the position of additional arguments, you can use placeholders:
p = _.partialRight(p, _, _, _, _, _, _, 56); // add 56 as 7th arg
p(1,2,3); // 1,2,3,,,,56
source to share
p = (function() {
var old_p = p;
return function(a, b, c) {
return old_p(a, b, c, 56);
};
})();
We remember the old version p
by name old_p
, so we can still call it even after we have overridden p
. We do this inside the IIFE so it old_p
doesn't pollute the global scope. We then return a function (which is assigned p
) that returns the result of the call old_p
with an additional argument.
We can make it more general to create "bound" functions that add additional arguments to any function call. Below I am using ES6 syntax, especially the spread operator ...
. However, you can do the same by manipulating the object arguments
and using apply
:
function bind_with_arguments_at_end(f, ...extra_args) {
return function(...args) {
return f(...args, ...extra_args);
}
}
If the function involved is a method on an object, it makes sense to "pass" that, so the new function can be named as this.bound_func
and everything continues to work. Do this, we can use call
:
function bind_with_arguments_at_end(f, ...extra_args) {
return function(...args) {
return f.call(this, ...args, ...extra_args);
^^^^^^^^^^^
}
}
You can create a new function that uses apply
to redirect its arguments back to the original one, but using Object.assign
to overwrite some of them:
function fixArguments(f, args) {
return function() {
return f.apply(this, Object.assign([].slice.call(arguments), args));
};
}
p = fixArguments(p, {3: 56}); // Overwrite the 4th argument with 56
function fixArguments(f, args) {
return function() {
return f.apply(this, Object.assign([].slice.call(arguments), args));
};
}
function p(x,y,z){
console.log(arguments);
}
p = fixArguments(p, {3: 56});
p(12,21,32);
source to share
Make a copy of the original and override the name and invoke the original with new arguments.
function p(a,b,c,d) {
console.log(arguments);
}
(function (){
var org_p = p; //copy original
p = function() { //override p
var args = [].slice.call( arguments ); //turn arguments in to array
args.push(56); //add the 4th argument
return org_p.apply( this, args ); //call the original with the updated arguments.
}
}());
p(1,2,3);
source to share