I have some code like this
var a = returnsABoolean();
var b = returnsABoolean();
if (!a || !b) {
} else {
doStuff();
}
How would I invert the test in the if-statement such that I can rewrite this as
var a = returnsABoolean();
var b = returnsABoolean();
if (someExpression) {
doStuff();
}
In other words, what test should I replace someExpression with to preserve the existing behaviour?
You need to apply De Morgan's theorem. Which states:
!A || !B == !(A && B)
Therefore your test can be re-written as:
if (a && b) {
doStuff();
}
Why does it work?
Basically, applying De Morgan's theorem you first rewrite your statement as:
if ( ! (a && b) ) {
} else {
doStuff();
}
Since we now want to invert !(a&&b) we simply remove the not:
if ( (a && b) ) {
doStuff();
}
De Morgan's law states that you can rewrite !a || !b as !(a&&b)
This also works the other way: !a && !b can be rewritten as !(a||b)
Simply assign the logical inverse of your conditional to your previous scope's "else" statement.
if( a && b ) {
doStuff();
}
Related
I am trying to find out the value of the second variable in the if statement without knowing what the variable is.
EX:
//a, b, and c are controlled by the user in input boxes.
let a = "Josh"
let b = "James"
let c = ""
if (a.length!== 0 && b.length !== 0|| a.length !== 0 && c.length !== 0){
Here I want to check if a equals the value that the length doesn't equal 0. In this case b.
Ex:
if (a == secondVariable){
alert("WOOH")
}
I know I can write
if (a.length !== 0 && b.length !== 0){
if (a == b){
alert("WOOH")
}
} else if (a.length !== 0 && c.length !== 0){
if (a == c){
alert("BOOH")
}
} else {
alert("")
}
But this is a lot of code and I have a lot more variables to check in my code. Is there a more efficient way to write this? Thank you
You can combine the ifs. Also you only need to check the length of one thing if you are also comparing it vs other thing. Also there is a shortcut coercing the length property to a boolean:
if (a.length && a == b) {
alert("WOOH");
}
if (a.length && a == c) {
alert("BOOH");
}
I have a function that returns a condition using four variables.
(payload, variables) => {
return payload.newMessage.lenderId === variables.lenderId && payload.newMessage.user.id === variables.authId
}
I want to be able to say C === D is only if C and D exists. What would be the optimal expression for this? So A === B is a sufficient condition if C and D doesn't exist, but if C and D exist, A === B and C === D both have to be met.
A and B must always be equal, and one of the following must be true:
There is no C
There is no D
C and D are equal
(A === B) && (!C || !D || C === D)
Beyond this construction, you should know what you mean by "exists" - is it enough that they not be undefined? Is it any truthy value? Etc.
function customCheck(a,b,c,d) {
const abComparison = a === b;
if (c && d) {
return abComparison && (c === d);
}
return abComparison;
}
From your description seems something like above?
I need to simplify this expression
var foo = (!A && B && C) || (A && B && !C) ;
Can anyone suggest a good simplification using minimal operators ?
B is common in both condition, for rest conditional operator can be used.
var foo = B && (A ? !C : C);
Its an XOR operation, do read Logical XOR in JavaScript
Since (!A && C) || (A && !C) is the expansion of XOR, you can replace that part with an XOR expression:
var foo = B && (!!A ^ !!C);
How can you write an or function without using || operator? ! and && are permissible.
var output = or(true, false);
console.log(output); // --> true;
There are two basic tautologies that you just have to combine. For any a, b:
De Morgan's law: !(a && b) if and only if !a || !b
Double negation: !!a if and only if a
Thus a || b if and only if !(!a && !b) so
function or(a, b) {
return !(!a && !b);
}
That being sad this is only true if a, b are boolean. Note that || operator in JavaScript has side effect:
> var a = 'foo';
> var b = 'bar';
> a || b
'foo'
but
> !(!a && !b)
true
I doubt this can be achieved solely with ! and &&. However this can be implemented without ||:
function or(a, b) {
if (a) {
return a;
}
return b;
}
This still is not 100% the same as ||. That's because a || b evaluates b only if a is false. In particular for functions f() || g() the call g() will be evaluated only when f() is false. So this is another side effect of || which I don't think can be emulated by a function at all.
When is or true?
Whenever either A is true or B is true -- but that answer includes the word "or".
So let's put it another way: whenever it is not the case that both A is false and B is false.
!a && !b = !(a || b)
!a || !b = !(a && b)
!(a || b) = (a || b) else
so to answer your question
!a && !b else // this is the or
but that is a horrible thing to do. Use positive logic and all the tools available to make your code readable.
Are you asking something like this?
var a;
var b = 3;
console.log(a || b);
console.log(!a && b);
Just because I wanted to prove to myself the original question is entirely possible ;) and I didn't use a |
function or(a, b){
var c = console.log;
console.log = function(input) {
c.apply(console, [input]);
window.output = !window.output;
}
return !(!a && !b);
}
// OP Question
var output = or(true, false);
console.log(output); // --> true;
console.log(output); // --> false;
From a bug report, I think that the following expression might throw an exception if x is null:
if ( !x || doSomething( x[prop], y[prop] ) === false )
The exception is:
Cannot read property 'prop' of null
... as if the right side of the || is evaluated even if the left side is true.
The javascript reference seems to indicate that that should not happen, but I'm not sure. I've tested that just writing x = null does not (always) crash, but is it guaranteed on every JS engine ?
EDIT:
Same question about
if( x && foo( x[prop] ) === true && bar() === false )
One way to put it is, does :
if( a && b && c )
... evaluates b or c if a === false ? The doc is not clear about that case, only for "a && ( expr1 && expr2 )", not "a && expr1 && expr2"
Full code snippet
var x = null;
var y = {
"p1": "p1",
"p2": "p2"
};
function f() {
return true;
}
for (var propName in y) {
if (x && f(y[propName]) === true && f(y[propName]) === false) {
doSomething(x[propName], y[propName]);
} else if (!x || f(x[propName], y[propName]) === false) {
console.log(y[propName]);
}
}
EDIT2: for completeness, the real (minimized) code that run in the browser
function a(c, b, e, f) {
for (var d in b) {
if (c && _.isObject(b[d]) === true && _.isArray(b[d]) === false) {
a(c[d], b[d], e, d + ".")
} else {
if (!c || _.isEqual(c[d], b[d]) === false) {
e.push({
name: f + d,
value: b[d]
})
}
}
}
return e
}
The Javascript || operator is short-circuiting. The right-hand side will not evaluate if the left-hand side is true. That's a fundamental property of the operator and should be equally implemented across all engines.
Therefore, the right-hand side will only evaluate if x is truthy, and all truthy values in Javascript should be subscriptable without error.
Having said that, y is completely unknown in this example and might throw an error.
"Is it guaranteed on every JS engine?"
We can't actually know that for sure, but the standard defines, how these operators should be implemented.
Logical OR:
Let lref be the result of evaluating LogicalORExpression.
Let lval be GetValue(lref).
If ToBoolean(lval) is true, return lval.
Let rref be the result of evaluating LogicalANDExpression.
Return GetValue(rref).
http://es5.github.io/#x11.11
Item 3 doesn't leave any room to doubts, lval is returned immediately if lref can be evaluated to truthy, and rref will never be evaluated.
if (typeof y != 'undefined' && typeof x != 'undefined' && x !== null && y !== null) {
if (doSomething( x[prop], y[prop] ) === false) {
//do stuff
}
}
do the safety check before. this should be working
but note:
if your prop Attribute does not exist, this will return an error too!
greetings