Which is right way to use below statement performance wise? - javascript

Which approach is most recommended. First or Second ?
var x = document.querySelectorAll("span");
// #1: Console returns false
x.length > 0 && x[0].blur();
// #2: Console returns undefined
if (x.length > 0) {
x[0].blur();
}

If you find x.length > 0 then you will definitely get x[0] and do not need to check && x[0].blur();. So your second approach is much better.
if (x.length > 0) {
x[0].blur();
}

Related

Having issues trying to fix this control flow problem

I've thought I figured out how basic javascript logic works, but here I must have forgot something.
let firstElementSavedIndex = 1
console.log(firstElementSavedIndex)
firstElementSavedIndex = 0;
console.log(firstElementSavedIndex)
if (firstElementSavedIndex !== undefined || firstElementSavedIndex !== 0) firstElementSavedIndex -= 1;
console.log(firstElementSavedIndex)
The code I created above I wanted to use as a guard to prevent firstElementSavedIndex from decrementing unless firstElementSavedIndex isn't undefined or 0.
However the code above decrements even if firstElementSavedIndex is 0.
I must be missing something basic, but I havent found any solutions so far.
Any help would be appreciated.
-Hendrik
In the if block the expression becomes
0 !== undefined || 0 !== 0
true || 0 !== 0
true
Since you are using or as long something evaluates to true the whole expression will become true hence the code goes inside the if block.
To fix this you need to replace || with && and make the conditional as savedIndex greater than 0.
let firstElementSavedIndex = 1;
console.log(firstElementSavedIndex);
firstElementSavedIndex = 0;
console.log(firstElementSavedIndex);
if (firstElementSavedIndex !== undefined && firstElementSavedIndex > 0) {
firstElementSavedIndex -= 1;
}
console.log(firstElementSavedIndex);
now it becomes
0 !== undefined && 0 > 0
true && 0 > 0
true && false
false

Why can't I assign and then check a variable in the same if statement in Javascript?

In other words, why doesn't this show an alert?
var x;
if (x = 1 && x > 0) {
alert(x);
}
As far as I understand, x = 1 should assign 1 to x and also return 1. The x > 0 check is failing. Why?
Actually, the && operation will have precedence over the assignment.
In you case, x will be the result of 1 && x > 0 which is false.
var x;
if (x = 1 && x > 0) {
alert(x);
}
console.log(x); // false
You can enforce the order of operations using parentheses, as shown by Nina Scholz.
You need some parens to separate the assignment from the ongoing expression.
var x;
if ((x = 1) && x > 0) {
alert(x);
}

Can this positive / negative check be simplified?

I basically want to check if newValue goes past targetValue. But targetValue could be either a positive or negative number, so if ( newValue < targetValue ) won't necessarily work.
I coded it the way below, and I may be overthinking things here but I wondered if there's a way to rewrite the if-check a bit more elegantly…
var newValue = 0;
function ChangeValue ( targetValue : int )
{
var isTargetPositive = ( targetValue > 0 );
if ( isTargetPositive && newValue < targetValue || !isTargetPositive && newValue > targetValue )
newValue = math.moveTowards( newValue, targetValue, 1 );
else
// Do something else
}
The only thing I can think of that keeps your conditions exactly as they are is removing the isTargetPositive variable and replacing your if statement with the following:
if ( targetValue > 0 ? newValue < targetValue : newValue > targetValue )
this is almost the same case as in my chess project where I changed:
if((obj.ActiveColor&&current_val>0) || (!obj.ActiveColor&&current_val<0)){}
with
var impossible_to_name = (current_val * (obj.ActiveColor?1:-1));
if(impossible_to_name>0){}
I know you don't need to cache the var, but in my case I was going to use it later so I cached it, my code is so complex that I couldn't even give a proper name to my var, I am also not entirely sure if this will help you, if I couldn't translate it into your code, chances are you can't neither but I will try to understand my code again and make an edit to my answer.
Note: my code was wrapped in if(current_val){...} so the value is anything except 0
var newValue = 0;
function ChangeValue ( targetValue )
{
if (
((targetValue > 0) && (newValue < targetValue))
||
((targetValue < 0) && (newValue > targetValue ))
)
{
newValue = math.moveTowards( newValue, targetValue, 1 );
}
else{
// Do something else
}
}
You can always make a subfunction if this is not clear enough
function abs_compare(target, number) {
return target != 0 && ((target > 0 && target > number) || target < number);
}
if (abs_higher(targetValue, newValue)) {
newValue = math.moveTowards(newValue, targetValue, 1);
}
I would also prefer target != 0 rather than double checking if it is superior or inferior to 0 because it is more clear in your condition statement that it is a forbidden value.
Also, Pointy said that since you have initialized newValue to 0, it will always remains to 0 which is currently false since ChangeValue is a function. The newValue can be changed before the function call.
UPDATE
I may have read too fast. Comparing target to 0 won't keep your actual logic and it is the same as the double check. Anyway, you can still use a function.
Also the best answer would rather be using the condition target > 0 ? target > number : target < number
Test (input: 5)
isTargetPositive - matched
newValue < targetValue - matched
Test (input: -1)
!isTargetPositive - matched
newValue > targetValue - matched
+ve or -ve integer, it will match the IF.
isTargetPositive && newValue < targetValue, same right? Why use &&?
I think one condition is enough.

What does shorthand "index >= 0 && count++" do?

I was killing time reading the underscore.string functions, when I found this weird shorthand:
function count (str, substr) {
var count = 0, index;
for (var i = 0; i < str.length;) {
index = str.indexOf(substr, i);
index >= 0 && count++; //what is this line doing?
i = i + (index >= 0 ? index : 0) + substr.length;
}
return count;
}
Legal: Think twice before using the function above without giving credit to underscore.string
I put the line alone here, so you don't waste time finding it:
index >= 0 && count++;
I have never seen anything similar to that. I am clueless in what is doing.
index >= 0 && count++;
First part: index >= 0
returns true if index has a value that is greater than or equal to 0.
Second part: a && b
most C-style languages shortcut the boolean || and && operators.
For an || operation, you only need to know that the first operand is true and the entire operation will return true.
For an && operation, you only need to know that the first operand is false and the entire operation will return false.
Third Part: count++
count++ is equivalent to count += 1 is equivalent to count = count + 1
All together now
If the first operand (index >= 0) of the line evaluates as true, the second operand (count++) will evaluate, so it's equivalent to:
if (index >= 0) {
count = count + 1;
}
JavaScript nuances
JavaScript is different from other C-style languages in that it has the concept of truthy and falsey values. If a value evaluates to false, 0, NaN, "", null, or undefined, it is falsey; all other values are truthy.
|| and && operators in JavaScript don't return boolean values, they return the last executed operand.
2 || 1 will return 2 because the first operand returned a truthy value, true or anything else will always return true, so no more of the operation needs to execute. Alternatively, null && 100 will return null because the first operand returned a falsey value.
It's equivalent to:
if (index >= 0) {
count = count + 1;
}
&& is the logical AND operator. If index >= 0 is true, then the right part is also evaluated, which increases count by one.
If index >= 0 is false, the right part is not evaluated, so count is not changed.
Also, the && is slightly faster than the if method, as seen in this JSPerf.
It's the same as:
if(index >= 0){
count++;
}
JavaScript will evaluate the left side (index >= 0), if it's false the && (AND) will short circuit (since false AND anything is false), thus not running `count++.
If it's (index >= 0) true, it evaluates the right side (count++), then it just ignores the output.

Multiple Logical Operators in javascript

I want to check the following
1: Is x a number
2. If x is less that 5 or greater than 15, sound alert
3. If all is ok, callMe()
var x = 10;
if (isNaN(x) && ((x < 5) || (x > 15))) {
alert('not allowed')
}
else
{
callMe();
}
What am I doing wrong?
var x = 10;
if (isNaN(x) || (x < 5) || (x > 15)) {
alert('not allowed')
}
else
{
callMe();
}
This way, if x is not a number you go directly to the alert. If it is a number, you go to the next check (is x < 5), and so on.
All the other answers about the && vs || are correct, I just wanted to add another thing:
The isNaN() function only checks whether the parameter is the constant NaN or not. It doesn't check whether the parameter is actually number or not. So:
isNaN(10) == false
isNaN('stackoverflow') == false
isNaN([1,2,3]) == false
isNaN({ 'prop' : 'value'}) == false
isNaN(NaN) == true
In other words, you cannot use it to check whether a given variable contains a number or not. To do that I'd suggest first running the variable through parseInt() or parseFloat() depending on what values you expect there. After that check for isNaN(), because these functions return only numbers or NaN. Also this will make sure that if you have a numeric string then it is also treated like a number.
var x = 10;
if (isNaN(x) || (x < 5) || (x > 15)) {
alert('not allowed')
}
else
{
callMe();
}

Categories

Resources