Types & Conditionals
PRIMITIVE TYPES
Not all variables are references to objects. Some variables are primitive types, which store values like "3", "7.2", "h", and "false". They are:
- byte: A 8-bit integer in the range -128...127. (One bit is the sign.)
- short: A 16-bit integer in the range -32768...32767.
- int: A 32-bit integer in the range -2147483648...2147483647.
- long: A 64-bit integer, range -9223372036854775808...9223372036854775807.
- double: A 64-bit floating-point number like 18.355625430920409.
- float: A 32-bit floating-point number; has fewer digits of precision.
- boolean: "true" or "false".
- char: A single character. (can be treat as numbers, never negative)
long values are written with an L on the end: long x = 43L
;
This tells the compiler to internally write out "43" in a 64-bit format. double
and float
values must have a decimal point: double y = 18.0
; float
values are written with an f at the end: float f = 43.9f
; ("f" and "l" are not case sensetive)
Object types | Primitive types | |
---|---|---|
Variable contains a | reference | value |
How defined? | class definition | built into Java |
How created? | "new" | "6", "3.4", "true" |
How initialized? | constructor | default (usually zero) |
How used? | methods | operators ("+", "*", etc.) |
Operations on int, long, short, and byte types.
1 | -x |
Except for "%", these operations are also available for doubles and floats. Floating-point division ("/") doesn't round to an integer, but it does round off after a certain number of bits determined by the storage space.
The java.lang
(automatically import) library has more operations in...
- the Math class.
1 | x = Math.abs(y); // Absolute value. |
Also see Math.sqrt
, Math.sin
, etc.
- the Integer class.
1 | int x = Integer.parseInt("1984"); // Convert a string to a number. |
- the Double class.
1 | double d = Double.parseDouble("3.14"); |
Converting types: integers can be assigned to variables of longer types.
1 | int i = 43; |
The string (int)
is called a cast, and it casts the long
into an int
. In the process, high bits will be lost if l does not fit in the range -2147483648...2147483647. Java won't let you compile "i = l" because it's trying to protect you from accidentally creating a nonsense value and a hard-to-find bug. Java requires you to explicitly cast longs to ints to show your acknowledgment that you may be destroying information.
Similarly, float f = 5.5f; double d = f;
is fine, but you need an explicit cast for double d = 5.5; float f = (float) d;
. Integers (even longs) can be directly assigned to floating-point variables (even floats) without a cast, but the reverse requires a cast because the number is truncated to an integer.
Boolean Values
A boolean value is either "true" or "false". Booleans have operations of their own, signified "&&" (and), "||" (or), and "!" (not).
a | b | a && b | a or b | !a |
---|---|---|---|---|
false | false | false | false | true |
false | true | false | true | |
true | false | false | true | false |
true | true | true | true |
Boolean values can be specified directly ("true", "false") or be created by the comparison operators "==", "<", ">", "<=", ">=", "!=" (not equal to).
1 | boolean x = 3 == 5; // x is now false. |
CONDITIONALS
An if
statement uses a boolean expression to decide whether to execute a set of statements. The form is:
1 | if (boolValue) { |
The statements are executed if and only if "boolValue" is "true". The parentheses around the boolean expression are required (for no good reason).
1 | boolean pass = score >= 75; |
if-then-else clauses can be:
- nested
- daisy-chained.
Nesting allows you to build decision trees.
Daisy-chaining allows you to present more than two alternatives.
For instance, suppose you want to find the maximum of three numbers.
1 | if (x > y) { |
Some long chains of if-then-else clauses can be simplified by using a switch
statement. switch
is appropriate only if every condition tests whether a variable x is equal to some constant.
1 | switch (month) { |
IMPORTANT: break
jumps to the end of the switch
statement. If you forget a break statement, the flow of execution will continue right through past the next "case" clause, which is why cases 4, 6, and 9 work right. If month == 12
in the following example, both Strings are printed.
1 | switch (month) { |
However, this is considered bad style, because it's hard to read and understand. If there's any chance that other people will need to read or modify your code (which is the norm when you program for a business), don't code it like this. Use break statements in the switch, and use subroutines to reuse code and clarify the control flow.
Observe that the last example doesn't have a default:
case. If month
is not 1 nor 2 nor 11 nor 12, Java jumps right to the end of the switch
statement (just past the closing brace) and continues execution from there.
THE return
KEYWORD
Like conditionals, return
affects the flow of control of a program. It causes a method to end immediately, so that control returns to the calling method.
Here's a recursive method that prints the numbers from 1 to x.
1 | public static void oneToX(int x) { |
The return keyword serves a dual purpose: it is also the means by which a function returns a value. A function is a method that is declared to return a non-void type. For instance, here's a function that returns an int.
1 | public int daysInMonth(int month) { |
The "return" value can be an expression. Some examples:
1 | return x + y - z; |