see http://webmail.mac.com source.
B.incompatible = !!(B.msie < 7 || B.safari < 500 || B.mozilla < 1.008000999);
B.unsupported = !!(B.opera || B.safari < 500) && !B.incompatible;
B.supported = !B.incompatible && !B.unsupported;
Why are the double "!" used here? Is there any benefit?
There is no point in this case, since the expressions already evaluate to boolean values anyway. It's probably just a programmer being "extra sure".
The logical NOT operator ("!") is used to convert true to false and vice versa.
! true // expresses false
! false // expresses true
However, it also coerces values. Non zero numbers and non empty strings are true. So they become false.
! 1.0 // expresses false
! 0.0 // expresses true
! '#' // expresses false
! '' // expresses true
Using two NOTs converts it back to the original Boolean value.
!! 1.0 // expresses true
!! 0.0 // expresses false
!! '#' // expresses true
!! '' // expresses false
It's equivalent to calling the Boolean constructor. However, it's faster (no function call overhead), shorter, and more readable.
!! 1.0 === Boolean(1.0) // expresses true
Its a very smart way of casting to a bool.
Related
I have this line of code in a js file
var useScroll = Window.innerWidth > 1360 ? true : false;
When it's minified it becomes
i=Window.innerWidth>1360?!0:!1
I was just curious, why have the ! operator? To me it makes more sense to just be.
i=Window.innerWidth>1360?1:0
The ! operator does casting. So !0 becomes true and !1 becomes false. However, 0 and 1 are numbers, not booleans.
There is a very valid reason. 1 and 0 are integeers, and does sometimes behave different than booleans.
However the ! operator includes casting, which menas that !0 and !1 are acutal booleans, but they are shorter to type than false and true. And that is the reason they are beeing used.
Example where they behave different:
var a = (1 === true); //a will be false
var a = (!0 === true); //a will be true
However you can simplify your code to
i=Window.innerWidth>1360
since Window.innerWidth>1360 will be either true or false which is exactly what you are looking for.
if you do !0 or !1 it will become a boolean, if you remove ! it will be an integer...
And instead of doing
Window.innerWidth > 1360 ? true : false
do
Window.innerWidth > 1360
The ! is (logical NOT) operator So !0 become true and !1 becomes false. Where only 0 and 1 are numbers not boolean.
var n1 = !true; // !t returns false
var n2 = !false; // !f returns true
var n3 = !'Cat'; // !t returns false
So, both have a different meaning by data types.
i=Window.innerWidth>1360?1:0 This is also valid as you told but when you want data type as boolean you can't get by using this expression.
This question already has answers here:
What is the !! (not not) operator in JavaScript?
(42 answers)
Closed 7 years ago.
I found some code about authentication with angular and i can't understand this trick :
authService.isAuthenticated = function () {
return !!Session.userId;
};
What does !! mean 'different of userId' ?
whenever true = !!true = !!!!true =>etc, it don't understand this.
Somebody can help me?
(https://medium.com/opinionated-angularjs/techniques-for-authentication-in-angularjs-applications-7bbf0346acec for the source , part 'The AuthService')
!! Converts any value to a boolean value
> !!null
false
> !!true
true
> !!{}
true
> !!false
false
If a value is falsey then the result will be false. If it is truthy the result will be true.
Even more, the third ! inverts the converted value so the above examples become:
> !!!null
true
> !!!true
false
> !!!{}
false
> !!!false
true
It forces what is returned to be a boolean and not an integer or empty value. For example, 0 evaluates to false with == but will not with ===. So to be sure that any integer 0 returned will be converted into an boolean, we use !!. This also works if null or undefined is returned.
So whats happening is actually:
var test = null;
var result = !test; // returns true
result = !return; // returns false
!! is used to convert the value to the right of it to its equivalent boolean value.
!!false === false
!!true === true
Coerces oObject to boolean. If it was falsey (e.g. 0, null, undefined, etc.), it will be false, otherwise, true.
!oObject //Inverted boolean
!!oObject //Non inverted boolean so true boolean representation
So !! is not an operator, it's just the ! operator twice.
Referred from : https://stackoverflow.com/a/784946/2218635
function grep( elems, callback, invert ) {
var callbackInverse,
matches = [],
i = 0,
length = elems.length,
callbackExpect = !invert;
// Go through the array, only saving the items
// that pass the validator function
for ( ; i < length; i++ ) {
callbackInverse = !callback( elems[ i ], i );
if ( callbackInverse !== callbackExpect ) {
matches.push( elems[ i ] );
}
}
return matches;
}
wouldn't this be more straight forward
for ( ; i < length; i++ ) {
callbackInverse = callback( elems[ i ], i );
if ( callbackInverse == callbackExpect ) {
matches.push( elems[ i ] );
}
}
I guess it's to make sure both variables are booleans.
For example, imagine callback returns NaN when running
callbackInverse = callback( elems[ i ], i );
That could be problematic, given that
NaN == true; // false
NaN == false; // false
(It happens because the comparisson of a boolean and a number coerced the boolean to a number, instead of coercing the number to boolean)
But negating the values with ! converts them to booleans, avoiding those problems.
Note that callbackExpect is set to !invert:
callbackExpect = !invert;
This forces callbackExpect to be a "boolean" (so exactly true or false).
Then they compare using !== which is not the same as != in that it compares the content of the variable without conversion. In other words, if callbackInverse is not exactly 0 or 1, it returns true.
Note that the inverse of !== is === and not == as in your example. i.e. compare without first converting the parameters.
Update:
As pointed out by Walter Tross in a comment, Boolean is a separate type:
// Booleans
typeof true === 'boolean';
typeof false === 'boolean';
typeof Boolean(true) === 'boolean'; // but never use this form!
Therefore the !invert generates a Boolean and if callbackInverse is not a Boolean, then !== is going to be true. However, like the callbackExpect variable, it is set to !(of something) which means it will always be a Boolean too. So you could use == and != since the ! operator is used to canonicalize the returned values.
Because this way both the invert param and the return value of the callback are cast to boolean by the !, so that they can be safely compared as booleans.
E.g., imagine callback returns undefined. But undefined != false, while you probably want undefined to be treated like false. In fact, casting it to boolean yields false:
!!undefined === false (!! is an easy way of casting to boolean).
Instead of doing the double negation, jQuery does a single one, negating the other side just once, before the loop, so that the comparison becomes:
!undefined === !false (this is a bit like changing the sign of both sides of an equation.)
Quoting the ECMAScript 5.1 standard:
Boolean comparison can be forced by: !a == !b.
The price of doing a single negation instead of a double negation inside the loop is readability (which is always impaired when using "negative logic"), but in a highly optimized library like jQuery this is acceptable.
As to your example, you should rename callbackInverse to something like callbackValue, since it's not inverted (and not cast to boolean) any more. But the problem remains: your code will only work correctly if callback is guaranteed to return booleans.
Many of us have seen / use the following:
var t=!0; (t will equal true)
var t=!1; (t will equal false)
How safe is this method of evaluating true / false?
I see google use this all the time.
Will these ALWAYS return a boolean true / false?
Thanks.
Yes:
11.4.9 Logical NOT Operator ( ! )
The production UnaryExpression : ! UnaryExpression is evaluated as
follows:
Let expr be the result of evaluating UnaryExpression.
Let oldValue be ToBoolean(GetValue(expr)).
If oldValue is true, return false.
Return true.
Source: http://es5.github.com/x11.html#x11.4.9
Yes, they'll always return true and false.
More specifically, !x will return true for any "falsey" value (undefined, "", etc) and conversely return false for any "truthy" value.
A more common idiom is !!x which converts any "falsey" value to strictly false and any "truthy" value to strictly true - in other words it's like a "type cast" to a boolean.
This question already has answers here:
Closed 12 years ago.
Possible Duplicate:
What is the !! operator in JavaScript?
Sorry if this one is obvious but I can't google it.
What is the "!!" operator in Javascript? e.g.
if (!!window.EventSource) {
var source = new EventSource('stream.php');
} else {
// Result to xhr polling :(
}
Did the author just use "!" twice i.e. a double negation? I'm confused because this is in the official doc.
It will convert anything to true or false:
!!0 // => false
!!1 // => true
!!'a' // => true
!!'' // => false
!!null // => false
Technically, !! is not an operator, it is just two ! operators next to each other. But a double-negation is pointless unless you are using !! like an operator to convert to Boolean type.
In most languages, !! is double negation, as ! is negation. Consider this:
# We know that...
!false == true
# And therefore...
!!false == false
!!true == true
It's often used to check whether a value exists and is not false, as such:
!!'some string' == true
!!123 == true
!!myVar == true
!! is used to convert a non-zero/non-null value to boolean true and a zero/null value to false.
E.g. if a = 4, then !a = false and !!a = !(!a) = true.