Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 5 years ago.
Improve this question
I did a little research, and the best answer I found is:
function overloading in js
Top 10 answers did gave me some hints and clues, but not the consistent way how to handle those situations in general.
Let's take a question a little further:
What if I am making API for someone else. That should give you the answer to following questions:
Why am I doing this?
JS doesn't have overriding in strict sense (yes I am aware, not the point)
Pass the object with optional parameters (Would prefer it, it's not up to me)
Specific solutions that assume types, fixed number of parameters, single values etc.
Some of the functions have to take many optional parameters (and some non-optional ones). So the function looks something like:
var f = function (unopt1, unopt2, op1, op2, op3) {
// code
}
The unoptX parameters are not optional.
The opX parameters are optional (in a sense they can be equal to 1 value from fixed set or values or not passed to function at all).
So function can be called in any of the following ways:
f("z", "b")
f("a", "b", 1, "ff");
f("a", "b", "ff", "hic");
f("a", "b", "ff", "no-hic");
etc.
Obviously, optional parameters each can have certain values, let's say they are listed in a certain order. And ofc. function behaves differently depending on the parameters
What would be your reccomended approach on this? Multiple ones are fine, prefferably you will point out what are ups/downs of certain approach over the other.
Use the spread operator as the argument:
function f(...args){
switch(args.length){
case 1:
get()
case 2:
set()
default:
setWithOptions()
}
}
Use an "options" object or ES6 "rest parameters"
var f = function (unopt1, unopt2, opts) {
opts = opts || {};
// later... if( opts.yourOptionalArg )
}
ES6 Rest Parameters
var f = function (unopt1, unopt2, ...args) {
console.log(args)
var firstOptionalArg = args[0];
}
Related
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 6 months ago.
Improve this question
I'm a huge fan of functional programming. I strive to use point free notation when I can. However, I often don't understand when point free notation is appropriate or when it is overkill. I typical delema that I run into is when I have a three or fewer functions that I would love to use a compose(...) statement for to avoid creating variables. However, I often feel like the code ends up looking uglier when I use compose(...) for such few functions compared to using intermediate variables.
Here's an example of my dilemma:
// Prefering point free notation
(address, signer, execute) =>
(atr, sequenceId) =>
compose(
setTxHash(atr, sequenceId),
execute(address, signer),
findTx,
)(atr, sequenceId);
// Preferring temporary variables
(address, signer, execute) =>
(atr, sequenceId) => {
const step1 = findTx(atr, sequenceId);
const step2 = execute(address, signer)(step1);
const step3 = setTxHash(atr, sequenceId)(step2);
return step3;
}
// function composition without using compose(...) method
(address, signer, execute) => (atr, sequenceId) =>
setTxHash(atr, sequenceId)(
execute(address, signer)(
findTx(atr, sequenceId)
)
)
I know asking "do any of these look better than others?" may be too subjective but are there any rules of thumb I can use or any good resources that talk about this and can offer a helpful perspective?
Thanks in advance!
If you need to introduce the points (variables with names) anyway because you're passing them to multiple functions, using compose is overkill. The third version of your function is the cleanest in that regard. Also, names are always useful if they are descriptive, since that aids the understandability of the code.
Only if you could write
(execute) => compose(
setTxHash,
execute,
findTx,
)
the usage of compose gains you anything (in particular, conciseness).
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 3 years ago.
Improve this question
I recently came across a question in an interview and am stumped at how to solve it. I would really appreciate any assistance.
The question asked me to create a function that received a number as a parameter (599) and returns a different number, but will also work in reverse. The issue is that I was not permitted to use any sort of conditional operator e.g. if, switch etc...
This was as far as I got:
function changeValue(v) {
// return 599 if 395 passed and vice versa
}
Use an object
function changeValue(v) {
const obj = {'395': 599, '599': 395};
return obj[v];
}
console.log(changeValue(395));
console.log(changeValue(599));
how about this:
function changeValue(v) {
return (599 + 395) - v;
}
from a programming perspective, this isn't as good a solution as the one that uses an object, because an object (map/dictionary) is easier to extend to other values.
Apart from the explicit memoization of the argument-result-pairs in an object (see other answer) you may use a linear function (remember it from math classes) f of the form f(x)=mx+b satisfying f(599)=395 and f(395)=599.
Solving this gives: m = -1, b = 994
function changeValue(v) {
return 994 - v;
}
console.log(changeValue(395));
console.log(changeValue(599));
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 6 years ago.
Improve this question
I needed to create a lot of entities in arrays at my job, and some guy said to me use this library to use "pattern matching" in my pull request instead creating manually the arrays an populating it.
We have to create a lot of things, eg. of user:
function createUser(id){
return {
id: id
}
}
var users = createStuff(createUser, 50);
what I did to populate:
function createStuff(createFunction, howManyTimes){
var createdStuffs = [];
for(var i = 0; i < howManyTimes; i++){
createdStuffs.push(createFunction(i));
}
return createdStuffs;
}
what he asked me to do with pattern matching:
function createStuff(createFunction, howManyTimes){
return howManyTimes.matches(
(x = 0) => [],
(x) => [createFunction(x)].concat(createStuff(createFunction, x - 1))
)
}
What is the benefits about this pattern matching? I do understand the recursive calling on his example which replaces the for loop, but I think my example is easier to read though all the creation logic is basically written at a single line at his example.
I'm asking explanations about this and most people are telling me "it's better because is functional and have less moving parts", is this really true? I don't agree with him and I'd like explanations or arguments to tell he's wrong
Your colleague has taken the quite correct premise that immutability and a functional style is beneficial and drawn a very incorrect conclusion that any immutable solution employing a functional style is superior. Readability is important and possible in any paradigm.
A proper functional solution using underscore.js with all the benefits and none of the eye-gouging readability issues would look like:
var users = _.map(_.range(howManyTimes), createUser);
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 6 years ago.
Improve this question
we did some code review and it the code before was like following:
run: () =>{
var _this = this;
return Promise.all([
//Get command
cp.getCommand(constants.HB),
//Find port
cp.findPort()
]).spread((r1, r2) => {
...
After the code review my colleagues suggest to change it to the following which I disagree
since you need to add unnecessary code (the array & push) and Im not sure that this is more readable, what do you think?
run: function () => {
var _this = this;
var promiseArray = [];
//Get command
promiseArray.push(cp.getCommand(constants.HB));
//Find port
promiseArray.push(cp.findPort());
return Promise.all(promiseArray)
.spread((r1, r2) => {
There is no particular reason to put the promises into an explicitly declared array before passing them to Promise.all() so it's pretty hard to defend that the second option is "better" than the first option.
In fact, you could easily make a case that the second option just creates an unnecessary named variable containing the intermediate array and does unnecessary .push() function calls.
In the end, there is no absolute right or wrong here. This is merely a matter of opinion on coding style. Code reviews are often part defensible logic and part reviewer's opinion. It appears you just ran into some opinion where the reviewer has a different opinion than you do.
If you want to push back on a review issue like this, then you should ask them to defend why they their method is necessarily better than your first approach.
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 8 years ago.
Improve this question
I have lot enough functions, which look like:
var functionName = function(e) {
//
};
where all the parameters are getting passed in in a single container e. Most times values are simple values (no functions), ex.:
{ parameter1: 1, parameter2: "Name", parameter3:{ subParameter1: "A"}}
But there're times when I pass in functions as in: { p2:function(){...} }
I have two options when it comes to utilising parameter values:
Options 1: get parameter values from the chain, starting from e: e.parameter1, e.parameter3.subParameter1 etc.
Option 2: use cached parameter values:
var parameter1 = e.parameter1;
var subParameter1 = e.parameter3.subParameter1;
The second option improves readability but increases the number of vars and the size of the code base. On another hand it's much drier when using long chains, i.e. e.p1.p2.p3 etc.
What reasoning should I use for choosing between those two options?
**Update 1 - the question sounds quite subjective, let me re-prase it.**
I don't mind using chains all the way, no local vars codebase is smaller, I can always figure out what's what, are the any cases when caching is a must?
A combination, based on depth(e.p1 vs e.p1.sp2.ssp3) and frequency of use. Deeper sub-properties and high usage of any sub-property both benefit from caching.
Nested property look ups can get costly, and caching the value after executing the look up once is valuable if you're going to use it a lot. This is only more efficient if you're accessing a particular property on the chain more than once, and the more you access it, the more you benefit from caching.
If you only have one level deep(e.p1, e.p2, e.p3) and you're only looking up each property value once, don't bother.
If you're accessing e.p1.sp2.ssp3 all throughout your function, cache it for sure.