Named parameter in Javascript without overriding the existing values - javascript

Here is the code that I got from this Named parameters in javascript:
var parameterfy = (function () {
var pattern = /function[^(]*\(([^)]*)\)/;
return function (func) {
// fails horribly for parameterless functions ;)
var args = func.toString().match(pattern)[1].split(/,\s*/);
return function () {
var named_params = arguments[arguments.length - 1];
if (typeof named_params === 'object') {
var params = [].slice.call(arguments, 0, -1);
if (params.length < args.length) {
for (var i = params.length, l = args.length; i < l; i++) {
params.push(named_params[args[i]]);
}
return func.apply(this, params);
}
}
return func.apply(null, arguments);
};
};
}());
var myObject = {
first: "",
second: "",
third: ""
};
var foo = parameterfy(function (a, b, c) {
//console.log('a is ' + a, ' | b is ' + b, ' | c is ' + c);
myObject.first = a;
myObject.second = b;
myObject.third = c;
console.log("first " + myObject.first + " second " + myObject.second + " third " + myObject.third);
});
foo(1, 2, 3); // gives 1, 2, 3
foo({a: 11, c: 13}); // gives 11, undefined, 13
foo({ a: 11, b:myObject.second, c: 13 }); // in order to avoid undefined, this is
Note that, in second instance of foo, I got undefined as I didn't pass b so I had to work around using third instance where I passed the current value of b.
Is there anyway to make it so that if I don't have to pass a value, for example, value of b in this case so that it still updates the given values of a and c but retains the value of b?

Something like the below may work:
var foo = parameterfy(function (a, b, c) {
//console.log('a is ' + a, ' | b is ' + b, ' | c is ' + c);
if(typeof a != 'undefined'){myObject.first = a;}
if(typeof b != 'undefined'){myObject.second = b;}
if(typeof c != 'undefined'){myObject.third = c;}
console.log("first " + myObject.first + " second " + myObject.second + " third " + myObject.third);
});

Here's the named parameter standard that has been successfully used for years and you should stick with it:
function myFunction(options) {
console.log(options.first);
console.log(options.second);
console.log(options.third);
}
myFunction({
first: 1,
second: 2,
third: 3
});

Related

Function Scope with multiple nested IIFE's

I'm having trouble with this JavaScript exercise. I'm given a function that defines three different variable/value pairs and within that function are multiple nested IIFEs that change those same values. The goal of the exercise is to change the variable's values to a certain value. So here is the code that I was presented:
var scopeExercise = function() {
var a = 1,
b = 2,
c = 3;
result = "a: " + a + ", b: " + b + ", c: " + c;
(function firstFunction() {
var b = 5,
c = 6;
(function secondFunction() {
var b = 8;
(function thirdFunction() {
var a = 7,
c = 9;
(function fourthFunction() {
var a = 1,
c = 8;
})();
})();
})();
})();
return result;
};
console.log(scopeExercise());
And they want the var a = 1, b = 8, and c = 6. I'm still having trouble understanding the function scope because I've tried commenting out the thirdFunction and fourthFunction so that they don't get called before the outer functions and it still won't change the values of var a, b, and c. Also, I don't understand why the nested functions aren't getting executed since they should be immediately invoked.
try this:
var scopeExercise = function () {
var a = 1, b = 2, c = 3;
(function firstFunction() {
b = 5;
c = 6;
console.log('firstFunction()');
(function secondFunction() {
b = 8;
console.log('secondFunction()');
(function thirdFunction() {
a = 7;
c = 8;
console.log('thirdFunction()');
(function fourthFunction() {
a = 1,
c = 6;
console.log('fourthFunction()');
})();
})();
})();
})();
result = "a: " + a + ", b: " + b + ", c: " + c;
return result;
}
console.log(scopeExercise());
added the prints that you will see that all functions were executed

which is the best way to write javascript ForEach

I heard forEach require a function that get 3 parameter, what about style 4 where parameters defined it. Why it's can work?
let arr = ["A", "B", "C", "D"];
//1
function temp(value, index, arr) {
console.log(value);
}
arr.forEach(temp);
//2
arr.forEach(function(value, index, arr) {
console.log(value);
});
//3
arr.forEach((value, index, arr) => {
console.log(value);
});
//4
arr.forEach(e =>
{
console.log(e);
});
The function definition defines the names of some variables that any arguments will be passed to.
That is all.
It does not enforce the number of arguments that can be passed.
You can pass any number of arguments to any function.
Some arguments might be ignored.
function myFunction(a, b, c) {
console.log("My function with " + arguments.length + " arguments");
console.log(a, b, c);
for (var i = 0; i < arguments.length; i++) {
console.log("Argument " + i + " is " + arguments[i]);
}
}
myFunction(100);
myFunction(200, 300, 400, 500, 600, 700);
function myFunctionWhichChecks(a, b, c) {
if (arguments.length !== 3) {
throw new Error("myFunctionWhichChecks must have exactly 3 arguments");
}
console.log("My function which checks has " + arguments.length + " arguments");
}
myFunctionWhichChecks(800, 900, 1000);
myFunctionWhichChecks(800, 900, 1000, 1100);

how do you write the code for mybind

I found this code in a book, how do you write or define the code for mybind
var concat = function(a, b) { return a + " " + b;}
var good = mybind(concat, "good");
good("night") == "good night"
To create a new function, you can either create it yourself:
function mybind(f, a) {
return function (b) {
return f(a, b);
}
}
var concat = function(a, b) { return a + " " + b;}
var good = mybind(concat, "good");
console.log(good("night"));
or for your scenario you can use function.bind to create one for you
function mybind(f, a) {
return f.bind(null, a);
}
var concat = function(a, b) { return a + " " + b;}
var good = mybind(concat, "good");
console.log(good("night"));
Like this:
var concat = function(a, b) { return a + " " + b;}
var mybind = function (fn, arg1) {
return function (arg2) {
return fn(arg1, arg2);
};
}
var good = mybind(concat, "good");
console.log(good("night") === "good night")
The following will make your comparison return true. myBind should create a new function bound to b. that's what bind does.
var mybind = function( fn, b ) { return fn.bind(this, b); };

Bind only second argument to javascript function

var add = function(a, b) {
return a + b;
}
var addOne =add.bind(null,1);
var result = addOne(4);
console.log(result);
Here the binded value of a is 1 and b is 4.
How to assign the binding value i.e)1 to the second argument of the function without using spread operator(...)
You could take a swap function with binding the final function.
var add = function (a, b) { console.log(a, b); return a + b; },
swap = function (a, b) { return this(b, a); },
addOne = swap.bind(add, 1),
result = addOne(4);
console.log(result);
With decorator, as georg suggested.
var add = function (a, b) { console.log(a, b); return a + b; },
swap = function (f) { return function (b, a) { return f.call(this, a, b) }; },
addOne = swap(add).bind(null, 1),
result = addOne(4);
console.log(result);
You could use the arguments object for reordering the parameters.
var add = function (a, b, c, d, e) {
console.log(a, b, c, d, e);
return a + b + c + d + e;
},
swap = function (f) {
return function () {
var arg = Array.apply(null, arguments);
return f.apply(this, [arg.pop()].concat(arg));
};
},
four = swap(add).bind(null, 2, 3, 4, 5),
result = four(1);
console.log(result);
You can use the following way
var add = function(x){
return function(y){
return x+y;
}
}
add(2)(3); // gives 5
var add5 = add(5);
add5(10); // gives 15
here add5() would set x = 5 for the function
This will help you what you need
var add = function(a) {
return function(b) {
return a + b;
};
}
var addOne = add(1);
var result = addOne(4);
console.log(result);
You can try this
function add (n) {
var func = function (x) {
if(typeof x==="undefined"){
x=0;
}
return add (n + x);
};
func.valueOf = func.toString = function () {
return n;
};
return func;
}
console.log(+add(1)(2));
console.log(+add(1)(2)(3));
console.log(+add(1)(2)(5)(8));

Dynamically generated object not working as parameter to .css()

I have this function:
function myfunc(obj, properties, value) {
$.each(properties, function(i, key) {
var a = '-webkit-border-' + key + '-radius';
var b = '-moz-border-radius-' + key.replace(/\-/g, '');
var c = 'border-' + key + '-radius';
var z = value+'px';
obj.css({a : z, b: z, c: z});
});
}
Called like this:
myfunc($tab, ['top-left', 'top-right'], defaults.tabRounded);
Note that if I replace the obj.css line with:
obj.css({'border-top-right-radius': value+'px'});
It works as intended. Yet the values of a, b, c are completely correct.
What is going on?
The keys of an object literal in JavaScript are strings, not variables. If you do not quote them yourself, they are auto-quoted. So if you write
var a = {b: 1};
it's the same as if you had written
var a = {'b': 1};
You have to use [] to set keys dynamically.
var a = {};
a[b] = 1;
In this case modify your function to
function myfunc(obj, properties, value) {
$.each(properties, function(i, key) {
var a = '-webkit-border-' + key + '-radius';
var b = '-moz-border-radius-' + key.replace(/\-/g, '');
var c = 'border-' + key + '-radius';
var z = value+'px';
var css = {};
css[a] = css[b] = css[c] = z;
obj.css(css);
});
}

Categories