-3

Why does the if-statement count as false?

int money = -342;
int reviews 3;

if (!(money > 0 || reviews < 5 || reviews > 0)){}

Money is false,
the both reviews are true
and inverting them results with a true for the money,
and two falses for both of the reviews.
As I am using || for ´or´, one true should be enough to make the whole of-statement become true.

shmosel
  • 49,289
  • 6
  • 73
  • 138
  • 1
    But money is not > 0, so that desn't make it true... – D M Feb 22 '18 at 20:49
  • 1
    I agree with @DM, -356 appears to be less than 0. – Jacob H Feb 22 '18 at 20:50
  • You are negating the or conditions with your `!`. So, while the or condition itself is `true`, it's negation is not. – GriffeyDog Feb 22 '18 at 20:51
  • 1
    Why would you say "_if not money is greater than 0_" rather than just "_if money less than 0_" – takendarkk Feb 22 '18 at 20:51
  • `!(false || true) == !true == false`. Also relevant: [De Morgan's laws](https://en.wikipedia.org/wiki/De_Morgan%27s_laws) (which tells you that `!(X || Y || Z) == !X && !Y && !Z`) – Bernhard Barker Feb 22 '18 at 20:51
  • If `Reviews < 5` is `false`, then `Reviews > 0` must be `true`, and vice versa. Therefore `Reviews < 5 || Reviews > 0` will always evaluate to `true` since at least one of the inequalities must be `true`. – Ted Hopp Feb 22 '18 at 20:57
  • Ted Hopp, what if reviews is `-1`, then it is less than zero and less than 5. – ifly6 Feb 22 '18 at 20:58
  • 1
    And **please follow the Java Naming Conventions**: variable names other than marked `static final` *always* start with lowercase. – MC Emperor Feb 22 '18 at 20:58
  • @ifly6 - Then `Reviews < 5` will be `true`. Regardless of the value of `Reviews`, at least one of the tests of `Reviews` will be `true`. – Ted Hopp Feb 22 '18 at 20:59
  • @MC Emperor as I´ve never heard of ´static final´ should I always start my variables with lowercase? – ThisIsCodeMaster Feb 23 '18 at 13:37
  • @ThisIsCodeMaster Yes, **always**. More precisely, variable names and method names must be in camelCase, class names PascalCase, package names all lowercase and constants UPPER_SNAKE_CASE. – MC Emperor Feb 23 '18 at 17:39
  • https://meta.stackexchange.com/q/116101/304954 – shmosel Feb 25 '18 at 17:49

10 Answers10

1

Your if test always evaluates to false because regardless of the value of Reviews, either Reviews < 5 or Reviews > 0 will be true and you are then negating the result. (The value of Money is irrelevant, since || evaluates to true if either operand is true.) I think what you want is for these three to be true:

  1. Money must be greater than 0
  2. Reviews must be between 0 and 5 (inclusive)

This if test will do the job:

if (Money <= 0 || Reviews > 5 || Reviews < 0) {
    System.out.println("Something went wrong");
} else {
    System.out.println("We're good");
}

Alternatively, you can test for the positive conditions:

if (Money > 0 && Reviews >= 0 && Reviews <= 5) {
    System.out.println("We're good");
} else {
    System.out.println("Something went wrong");
}
Przemysław Moskal
  • 3,551
  • 2
  • 12
  • 21
Ted Hopp
  • 232,168
  • 48
  • 399
  • 521
0

The negation symbol is negating the entire statement. Thus, if any of those conditionals are true then false is returned. If all conditionals are false then true is returned.

sellc
  • 380
  • 1
  • 5
  • 19
0

Because the following:

if (!(Money > 0 || Reviews < 5 || Reviews > 0))

evaluates to

if (!(True))

thus, inverted,

if (False)
ifly6
  • 5,003
  • 2
  • 24
  • 47
Doberon
  • 611
  • 9
  • 19
0

The parentheses take precedence.

Take a look at the condition:

(!(money > 0 || reviews < 5 || reviews > 0))

First, the part inside the inner parenthesis are evaluated:

money > 0 || reviews < 5 || reviews > 0

Then, the order is from left to right:

  • money > 0 is false, continue to next;
  • reviews < 5 is true, so the expression in the inner parentheses is true.

The expression within the inner parentheses evaluates to true, so effectively your condition is equal to !(true) and that makes (false).

I suggest you study the basics of expression evaluation and operator precedence. Also, as pointed out by Ted Hopp, you need to rethink your logic. For example, I would rewrite expressions like !(money > 0) to money <= 0, to simplify it. In my opinion, it's best to not use the negation operator (!) in conjunction with relational operators (like < or ==), unless you absolutely have to.


Note:

The && and || operators perform Conditional-AND and Conditional-OR operations on two boolean expressions. These operators exhibit "short-circuiting" behavior, which means that the second operand is evaluated only if needed.

MC Emperor
  • 22,334
  • 15
  • 80
  • 130
0

if (!(Money > 0)){...} - It says Something went wrong as the Money integer is below 0. - No, it says it's below or equal to 0.

(Money > 0 || Reviews < 5 || Reviews > 0) - this is true if at least one of parts between || is true, but:

!(Money > 0 || Reviews < 5 || Reviews > 0) - this is false if at least one of parts between || is true. You get an opposite result with ! (negation).

Przemysław Moskal
  • 3,551
  • 2
  • 12
  • 21
0

Why your value is false

Money is less than zero. That is false.

Reviews is less than 5. That is true.

It then short-circuits, but if you continued, Reviews is greater than 0. That is true.

Regardless, the whole statement in the brackets evaluates to true because of how an or operator works. You then invert it, so it turns into false.

A solution?

Honestly, it seems that what you want is a check that money is greater than 0, that reviews is less than 5 and that reviews is greater than 0.

This means that you should probably have something like money > 0 && reviews <= 5 && reviews >= 0. I assume that reviews here is something like a 0-5 star range. Obviously, if it were 1 to 5, that would be different.

ifly6
  • 5,003
  • 2
  • 24
  • 47
  • But after the inversion, the money is `true` and both of the reviews are `false` so overall, it should still be true. Or is it so that 2 `false` are more than 1 `true` so overall, the majority decides what the statement really is? – ThisIsCodeMaster Feb 22 '18 at 21:03
  • `money` is -356. That is less than zero. The expression `money > 0` is false. The other expressions, that `reviews < 5` and `reviews > 0` are true. An OR statement operates on a 'of all, if any are true, evaluate to true' – ifly6 Feb 22 '18 at 21:06
  • To be more clear, the inversion does not apply distributively to each test. – ifly6 Feb 22 '18 at 21:56
0
!(Money > 0) == (Money <= 0)

!(Money > 0 || Reviews < 5 || Reviews > 0) == (Money <= 0 && Reviews >= 5 && Reviews <= 0)

It is better not to use ! before the whole statement.

daddykom
  • 222
  • 2
  • 8
0

Thats because it is satisfying the Reviews < 5 and Reviews > 0 to true. So the if statement in if (!(Money > 0 || Reviews < 5 || Reviews > 0)) will be false because you are using not operator.Thats the reason it prints We´re good.

was_777
  • 599
  • 1
  • 9
  • 28
0

Umm. wait I've been doing this for a few years now and I'm pretty sure that the "!" also applys to the "||" thus making it an "&&" meaning it will always be false.

0

Let's understand your code conditions step by step:

    int Money = -356;
    double Reviews = 4.8;

    if (!(Money > 0 || Reviews < 5 || Reviews > 0)) {
        System.out.println("Something went wrong");
    } else{
        System.out.println("We´re good");
    }

Given :

  • Money = -356
  • Reviews = 4.8

Let's break and evaluate the inner if condition first: (Money > 0 || Reviews < 5 || Reviews > 0)

 1. Money   > 0      -356 > 0           **False**  
 2. Reviews < 5       4.8 < 5           **True**
 3. Reviews > 0       4.8 > 0           **True**

Now as we can see inner conditions evaluate True but if you notice there is a (logical not) " ! " operator added outside.

(!(Money > 0 || Reviews < 5 || Reviews > 0))

Called Logical NOT Operator. Use to reverses the logical state of its operand. If a condition is true then Logical NOT operator will make false.

Hence when your inner condition is True the Logical not ! makes it False.

So, System.out.println("We´re good"); Is executed.

Abhi
  • 995
  • 1
  • 8
  • 12