Unit 2, Chapter 2.5: Compound Boolean Expressions
Welcome! So far, you have learned how to use if statements to make decisions based on a single condition, like \( (score > 90) \). But in the real world (and in complex coding), decisions usually depend on multiple factors. For example, you might go to the park if it is sunny AND if you have finished your homework. In this chapter, we will learn how to combine simple conditions into Compound Boolean Expressions using logical operators.
Don't worry if this seems a bit "mathy" at first! We use this kind of logic every day without thinking about it. By the end of these notes, you will be able to write sophisticated conditions that make your programs much smarter.
1. The Three Logical Operators
In Java, we use three main symbols to build compound expressions. These operators work only with boolean values (\( true \) or \( false \)).
A. The NOT Operator: \( ! \)
The exclamation point is the "opposite" operator. It takes whatever boolean value follows it and flips it to the other side.
• \( !true \) becomes \( false \)
• \( !false \) becomes \( true \)
B. The AND Operator: \( \&\& \)
The double ampersand represents AND. For the entire expression to be \( true \), both sides of the operator must be \( true \).
• \( true \&\& true \) is \( true \)
• \( true \&\& false \) is \( false \)
• \( false \&\& true \) is \( false \)
• \( false \&\& false \) is \( false \)
C. The OR Operator: \( || \)
The double "pipes" (usually found above the Enter key) represent OR. For the entire expression to be \( true \), at least one side must be \( true \).
• \( true || true \) is \( true \)
• \( true || false \) is \( true \)
• \( false || true \) is \( true \)
• \( false || false \) is \( false \)
Key Takeaway: Use \( \&\& \) when you need all conditions to be met. Use \( || \) when you only need one of the conditions to be met.
2. Truth Tables: A Quick Reference
A truth table is just a fancy way of showing every possible outcome. If we have two boolean variables, \( A \) and \( B \), here is how they interact:
The AND Table (\( A \&\& B \))
1. \( true \&\& true \implies true \)
2. \( true \&\& false \implies false \)
3. \( false \&\& true \implies false \)
4. \( false \&\& false \implies false \)
The OR Table (\( A || B \))
1. \( true || true \implies true \)
2. \( true || false \implies true \)
3. \( false || true \implies true \)
4. \( false || false \implies false \)
Analogy: Imagine a teacher says, "To pass, you must turn in the essay AND take the final." If you miss either one, you don't pass. But if the teacher says, "To get extra credit, you can wash the boards OR organize the bookshelf," you only need to do one of them to get the credit!
3. Precedence: The "Order of Operations" for Logic
Just like in math where you do multiplication before addition (PEMDAS), Java has a specific order for evaluating logical operators. If you have a long expression without parentheses, Java follows this order:
1. NOT \( ( ! ) \)
2. AND \( ( \&\& ) \)
3. OR \( ( || ) \)
Example: How would Java evaluate \( !false || true \&\& false \)?
1. First, it does the NOT: \( !false \) becomes \( true \). Now we have \( true || true \&\& false \).
2. Next, it does the AND: \( true \&\& false \) becomes \( false \). Now we have \( true || false \).
3. Finally, it does the OR: \( true || false \) results in \( true \).
Pro-Tip: When in doubt, use parentheses! They are always evaluated first and make your code much easier for humans to read. For example, \( (A || B) \&\& C \) is very different from \( A || (B \&\& C) \).
4. Short-Circuit Evaluation
Java is "lazy" in a very efficient way. When evaluating compound expressions, it stops as soon as it knows the final answer. This is called Short-Circuit Evaluation.
Short-Circuit AND (\( \&\& \)): If the first condition is \( false \), the whole expression must be \( false \). Java doesn't even bother looking at the second condition.
Example: \( (5 > 10) \&\& (someComplexMethod()) \). Since \( 5 > 10 \) is \( false \), Java skips the second part entirely.
Short-Circuit OR (\( || \)): If the first condition is \( true \), the whole expression must be \( true \). Java stops right there.
Example: \( (10 > 5) || (anotherComplexMethod()) \). Since \( 10 > 5 \) is \( true \), Java doesn't check the second part.
Did you know? Short-circuiting is often used to prevent errors! For example, if you want to check if a String is not null before checking its length, you could write: \( (myString != null) \&\& (myString.length() > 0) \). If the String is null, Java stops before it hits the code that would cause a crash!
5. Common Pitfalls to Avoid
Mistake 1: Comparing one variable to two values incorrectly.
In English, we say "If x is 5 or 6." In Java, you cannot write \( if (x == 5 || 6) \). This will cause a compiler error because \( 6 \) is not a boolean. You must write: \( if (x == 5 || x == 6) \).
Mistake 2: Confusing AND and OR for ranges.
To check if a number is between 1 and 10, you must use AND: \( (num >= 1 \&\& num <= 10) \).
If you use OR: \( (num >= 1 || num <= 10) \), the expression will always be true because every number is either greater than 1 or less than 10!
Mistake 3: Forgetting that \( ! \) only applies to what is immediately next to it.
\( !x == 5 \) is not the same as \( !(x == 5) \). The first one tries to "flip" \( x \) (which only works if \( x \) is a boolean), while the second one checks if \( x \) is 5 and then flips that result.
Quick Review Box
• \( ! \) (NOT): Flips the value.
• \( \&\& \) (AND): Both must be \( true \).
• \( || \) (OR): At least one must be \( true \).
• Precedence: \( ! \) then \( \&\& \) then \( || \).
• Short-Circuit: Java stops early if the result is already guaranteed.