Javascript: var1 == true && (var2 = true) - javascript

I see in the code I am working on often the following code style;
var1 == true && (var2 = true)
After some testing I figured it comes down to:
if (var1 == true) {
var2 = true;
}
Is this correct, or is there more to it? And why would anyone use this since the readability just dramatically reduces, since your assume at first glance it is just a check on two variables. So you really have to start looking at single or double equal sings and where the parentheses are, which just kinda, you know.. Just curious here..

Yes, this is equivalent. As far as I know, it is called short-circuit evaluation, describing the fact that the interpreter will return false for the whole boolean expression as soon as one of its parts is falsy.
Indeed, in your example it DOES reduce readability. But I think of it as just another tool in your toolbox you may use when you feel it could be useful. Consider the following:
return user && user.name;
This is one example when I tend to use it. In this case, I think it's actually more readable than
if (user) {
return user.name;
} else {
return undefined; // or null or something alike
}
UPDATE
I want to give you another example when I consider this kinds of constructs useful. Think of ES6 arrow functions like user => user.name. It does not need {} to open a body since it just has one line. If you wish to log something to the console (for debugging), you would end up having
user => {
console.log(user); // or something alike
return user.name;
}
You might as well use the shorter variant
user => console.log(user) || user.name
since console.log returns undefined after logging into the console, hence user.name is returned.

Yes, as you've mentioned there's more to it.
the first part var1 == true checks whether ther result is true or false.
if the condition is false the code after it doesn't get checked or evaluated and thus var2 doesn't get set to true.
But if the first part of the condition var1 == true is true which obviously is true, the second part of the conditional statement the part after && is checked.
now the second part of the condition is an operation it sets (var2 = true) which is kind of a truthy operation.
we could edit your code a little bit to help you understand the operation more clearly:
if( var1 === true && (var2 = true)){console.log('good');}
I hope this helps

Related

Javascript boolean logic (comparing double bang with truthy/falsy values)

I'm inspecting some code and I found something I'd like to run by Javascript veterans. I feel pretty comfortable with Javascript but I've always manage to run into something that makes me say, "I didn't know that about Javascript!"
I'm hoping this is one of those situations:
if (this.props.referralId != prevProps.referralId ||
this.props.referralValidationStatus != prevProps.referralValidationStatus ||
this.props.customerName != prevProps.customerName &&
!!prevProps.personId != !this.props.personId) {
// perform whatever logic is here...
}
My questions:
Does JS know how to automatically identify the mixture of || and &&? Or is this code missing parenthesis's around the || comparison?
Just as it's explained here, is it fair and should I expect the obvious behavior when comparing a boolean against a truthy/falsy value?
I'm baffled on what the logic should be here. If I were to rewrite this I would do like so:
if ((this.props.referralId !== prevProps.referralId ||
this.props.referralValidationStatus !== prevProps.referralValidationStatus ||
this.props.customerName !== prevProps.customerName)
&& (!!prevProps.personId === !!this.props.personId)) {
// Perform logic
}
However, I'd like to confirm and make sure I'm not missing something I might have missed about JS.
Thank you in advance for confirming my hunch or educating my on something new when it comes to JS. Looking forward to your comments and/or answers.
Like most languages, there's a precedence rule in Javascript. && are evaluated before || as you can see here. So, if you need to check all the ors and then use the final result to make the and, you are right! Use the parenthesis.
You are also right about the !! refactoring:
!!prevProps.personId != !this.props.personId
Is the same as:
!!prevProps.personId === !!this.props.personId
In other words it is checking if both prevProps.personId and this.props.personId has some value (evalatued to True as boolean), or if both are empty/undefined/Nan (evaluated to False as boolean).
The first statement says (pseudocode):
if (
//the first statement returns truthy
this.props.referralId != prevProps.referralId ||
// or the second statement returns truthy
this.props.referralValidationStatus != prevProps.referralValidationStatus ||
// or the combination of the third and fourth statements returns truthy
this.props.customerName != prevProps.customerName
&&
!!prevProps.personId != !this.props.personId
)
// then...
{
// perform whatever logic is here
}
Your rewritten version says (pseudocode):
if (
// one of these three statements is truthy
(this.props.referralId !== prevProps.referralId ||
this.props.referralValidationStatus !== prevProps.referralValidationStatus ||
this.props.customerName !== prevProps.customerName)
&& // AND!
// this statement also evaluates truthy
(!!prevProps.personId === !!this.props.personId)
)
// then...
{
// perform whatever logic is here
}
Hopefully this explains the differences between the code blocks.
#rafaelodon is otherwise correct

testing whether property exists on an object and is equal to a certain value

let's say that we have an javascript object like below:
let obj = {name: 'firstName'};
which is a better way to test whether a property exists on an object and is equal to something:
1)
if (obj.address === 'someAddress')
or
2)
if (!!obj.address && obj.address === 'someAddress')
Can someone explain which is better/safer and why?
You asked "safer" and "better". "Better" is subjective as long as you don't define what qualities you're looking for, so I'll ignore that part.
Accessing a property that doesn't exist is valid in JavaScript, and simply returns undefined. So the second way is equivalent to:
const address = obj.address
if (!!address && address === 'someAddress') {
...
}
Now you can see that that's plain silly, because the second condition implies the first. In other words, there is no way that address === 'someAddress' can be true and !!address can be false, so there is no need to do the first check at all.
So the second approach is not safer than the first. Both have the same observable effect.
Nitpicker's corner: if you were checking for some falsy value like 0 or "" instead of the truthy string 'someAddress', then the second approach would not even work, because both conditions can never be true at the same time.
Also, if address is a property with an evil getter that may return a different value each time it's called, all bets are off. The first version could actually be safer because it only gets the value once, but presumably the value would be used inside the if block so the code is still broken.
1 is shorter :D and it works :D
Better is:
if (obj?.address === 'someAddress')
it checks both conditions

Edit : if statement when checking for false (if(variable){} equivalent for false)

Context : I am trying to reduce my code for a reactjs project that I am working on using expo. In one of my if else statements, one boolean variable's value is changed based on whether any of multiple other boolean variables are false. I wanted to make this much more optimized and remove unnecessary code since its for a mobile app.
My question is : Is there a way to make an if statement shorter while checking whether a variable is false?
if(variable){}
is the same as
if(variable === true){}
Is there a way like this for false as well? Maybe something like
if(!variable){}
I'm not exactly sure and couldn't find any method similar to what I showed above anywhere online (yet).
Example of the code I have right now :
var example = false
if(var1 === false || var2 === false || var3 === false || var4 == false){
example = true
}
if any of the variables are false (hence the ||), it should switch over
Thanks in advance!
This should be exactly the same as long as varN is already a boolean:
var example = false
if(var1 && var2 && var3 && var4){
example = true
}
But it must by said that premature optimizations rarely lead to improvements. Most often the interpreter already takes care of any optimizations like that. And the speed-increas one can get by changing simple comparisons are close to none.
So I would rather keep it in the most readable state than the most optimized.
Here's a shorter version:
var example = false
if (!(var1 && var2 && var3 && var4)) {
example = true
}
I wouldn't call this "optimization" and I don't think there's anything wrong with your code to begin with.
Edited:
you can use some()
if([var1,var2,var3,var4].some((item)=> item === false) ){
example = true
}

Optimizing conditionals/if blocks, what is preferable from a performance point of view?

I am writing a JS library, and there are two things that have been on my mind for quite some time though.
Consider an option:
var option = { bool : true } ;
Now, imagine I do either
if(option.bool)
or
if(option.bool === true)
The first case, despite knowing for sure that it's either true or false, I imagine is the equivalent of:
var tmp = options.bool;
if ( tmp !== undefined && tmp !== null && ( tmp === true || tmp ... )
That means that to try the options.bool = true it has to check both undefined and not null, before testing for true.
Therefore the latter case should be more performant. However, the latter case, takes a considerably more characters and will lead to a larger lib, if repeated many times.
But maybe my understanding is incorrect.
Right now, even if I do:
var bool = window.t ? true : false;
if ( bool === true ) // I still have to check for true to 'have the optmimal version'?
Maybe the last case can be optimized by the compiler, but when it's a global option I imagine it's different?
Please share with me your thoughts on this.
The answer is simple. It's less about coding patterns and more about logic.
In this scenario there are always 3 possibilities and you need to cater for each of them.
Ie. 1. TRUE 2. FALSE 3. undefined
If the value is undefined then do you want it to fall under the true or false clause? OR should it be catered for differently?
Another important thing to remember is that if it is undefined then it will always execute the code in the false clause. Is that what you want?
If you know that the value will always be either true or false then I suggest that you still use the syntax == true as this is more readable. Someone browsing over the code would know that you are looking for the boolean value and not testing if the field has been set.
You have to think about these 3 cases every time you have a boolean in an if statement, so there is no 1 answer for you.

Javascript best practice to use undefined as boolean evaluation?

In this simple javascript code, method verify returns a string if conditions do not match, else undefined. I am using undefined value in 'if' clause. Is this common / acceptable javascript programming practice?
if (verify(text)) {
alert(text + " is not bar");
}
function verify(foo) {
if (foo + "" != "bar") return "foo is not same as bar";
}
Yes, since you know the verification outcomes will be either truthy (a non-empty string) or falsy (undefined), it's perfectly fine to use it like that.
Here's a list of truthy and falsy values in JS, you might find them handy: http://www.sitepoint.com/javascript-truthy-falsy/
It is a common practise but in my experience its better to be explicit. For instance, I prefer:
verify(text) === undefined
The way I would suggest is to make the 'verify' to return a boolean value. The reason for this, is if for whatever reason you have a verification method that returns 0 (zero) and you do if (verify), the condition will be false but 0 is actually a verified value.
I hope that helps.
Although this is technically possible and works fine in most cases, I personally find it better style to design functions so that they always return the same type. My IDE warns me about inconsistent functions:
and this warning should be taken seriously. In particular, it helps you avoid unpleasant surprises when you test your app:
// hmm...
function isZero(n) {
if(n == 0)
return true;
}
// let's test it
describe("test", function() {
it("isZero", function() {
expect(isZero(0)).toBe(true);
expect(isZero(1)).toBe(false); // FAILURE!
});
});

Categories