## 1. De Morgan's Laws

### De Morgan's Laws

De Morgan's laws allow you to freely convert two types of boolean expressions:

```public class MyProgram {
public static void main(String[] args) {
boolean a = true;
boolean b = false;

//These two are the same:
System.out.println( !( a && b ) ); //NOT (a AND b)
System.out.println( !a || !b ); //(NOT a) OR (NOT b)

//These two are the same:
System.out.println( !( a || b ) ); //NOT (a OR b)
System.out.println( !a && !b ); //NOT a AND NOT b
}
}
```

These rules can also be used to break up longer expressions, such as:

public class MyProgram { public static void main(String[] args) { boolean a = true; boolean b = true; //try setting any one to false boolean c = true; boolean d = true; //If one is false, then the whole expression is true: System.out.println( !( a && b && c && d ) ); System.out.println( !a || !b || !c || !d ); } }

## 2. Truth Tables

### Truth Table

Boolean logic can get fairly complex when chained using the AND (&&) and OR (||) opeartors. One way to analyze, and perhaps simplify, boolean expressions is to create truth tables. A truth table for a boolean expression lists out the expression's values given different values for its boolean variables. For example, for the following expression: (!a && b) || !c || !a, we can construct a truth table as follows:

a b c (!a && b) || !c || !a
`false` `false` `false` `true`
`false` `false` `true` `true`
`false` `true` `false` `true`
`false` `true` `true` `true`
`true` `false` `false` `true`
`true` `false` `true` `false`
`true` `true` `false` `true`
`true` `true` `true` `false`

The above expression is actually equivalent to the simpler expression: !(a && c); we can verify that they are equivalent by creating a truth table for the simpler expression.

</tk>
a b c !(a && c)
`false` `false` `false` `true`
`false` `false` `true` `true`
`false` `true` `false` `true`
`false` `true` `true` `true`
`true` `false` `false` `true`
`true` `false` `true` `false`
`true` `true` `false` `true`
`true` `true` `true` `false`
Note that the values in both tables are equivalent.

## 3. Short Circuiting

### Short circuiting

Short circuiting is a powerful but simple feature. It states that:

• In an AND expression, if the left side is false, the right side will not be executed.
• In an OR expression, if the left side is true, the right side will not be executed.

The logic for short circuiting is that once one side of an AND is false, the whole expression must be false. Thus, the outcome of the expression does not depend on the right side.

### The impact of short circuiting

We will find short circuiting much more useful later, but here is a short example:

```public class MyProgram {
public static void main(String[] args) {
int x = 0;
if( true && 1==(x=1) ) {
System.out.println(x);
//This prints 1, since 1==(x=1) assigns 1 to x
//Then it evaluates to true
}

if( true || 2==(x=2) ) { //short circuits
System.out.println(x); //x is still 1
//2==(x=2) is never evaluated, since the || is already false
}

if( false && 3==(x=3) ) { //short circuits
//this does not run
}
System.out.println(x); //x is still 1

if( false || 4==(x=4) ) { //no short circuiting
//this does not run
}
System.out.println(x); //x is 4
}
}
```

Advanced students should note that short circuiting will be very powerful for avoiding array index out of bound errors. Short circuiting can also be used to conditionally execute functions when an expression is true. Use these features with caution, as they are not immediately obvious when reading code.