AP® Computer Science A review sheet from Aim for Five (aimforfive.com/csa/units/1/1-5)
Unit 1 · Topic 1.5
1.5 Casting and Range of Variables
Casting lets you convert between int and double on purpose, and the exam loves to ask exactly when the conversion happens. This topic also covers the limits of each type: int values can overflow, and double values can pick up tiny round-off errors.
Key terms
- casting
- truncation
- widening
Integer.MAX_VALUE- integer overflow
- round-off error
Casting between int and double
A cast is a type name in parentheses placed in front of a value: (int) or (double). It converts that value to the named type.
Casting a double to an int truncates it, which means it chops off everything after the decimal point. It does not round. (int) 3.9 is 3, and (int) -3.9 is -3.
Casting an int to a double adds a decimal part of zero, which matters because it makes division exact: (double) 7 / 2 is 3.5.
A cast applies only to the value right after it, and it happens before *, /, %, + and -. So where you put the parentheses changes the answer:
| Expression | What happens | Value |
|---|---|---|
| (double) 7 / 2 | 7 becomes 7.0, then 7.0 / 2 | 3.5 |
| 7 / (double) 2 | 2 becomes 2.0, then 7 / 2.0 | 3.5 |
| (double) (7 / 2) | Integer division first gives 3, then 3.0 | 3.0 |
| (int) 7.8 / 2 | 7.8 becomes 7, then 7 / 2 | 3 |
Automatic widening
Some conversions happen automatically. Java will widen an int to a double whenever it needs to, because no information is lost: double d = 10; stores 10.0, and in 5 * 2.0 the 5 is widened before multiplying. Java never narrows a double to an int on its own; you have to cast.
Rounding with a cast
There's no rounding method in this course's Java Quick Reference, so you round with casting. For a non-negative double x, (int) (x + 0.5) rounds to the nearest integer: 2.5 becomes 3, and 2.49 becomes 2. For a negative x, use (int) (x - 0.5): -2.7 becomes -3.
double avg = 7.8;
int whole = (int) avg;
int r = (int) (avg + 0.5);
System.out.println(whole + " " + r);
This prints 7 8: truncating 7.8 gives 7, and rounding gives 8.
Limits: overflow and round-off
An int is stored in 4 bytes of memory, so it can only hold values from Integer.MIN_VALUE (-2147483648) to Integer.MAX_VALUE (2147483647), inclusive. If a calculation goes past either end, you get integer overflow: the result wraps around to a value that's in range but wrong. There's no error message.
int big = Integer.MAX_VALUE;
big = big + 1;
System.out.println(big);
This prints -2147483648, the smallest int, not 2147483648.
A double has limited precision, so some decimal values can't be stored exactly. The stored value is rounded to the closest one that fits, which causes round-off errors: 0.1 + 0.2 prints as 0.30000000000000004. If you need exact results, such as money, store whole numbers in an int (like cents instead of dollars). Special decimal classes that avoid round-off aren't part of the course.
Worked examples
Try each one yourself first, then open the solution.
- Example 1
Exact average, then rounded
What does this code print?
int total = 47; int count = 6; double avg = (double) total / count; int rounded = (int) (avg + 0.5); System.out.println(avg); System.out.println(rounded);Show the solutionHide the solution
- Step 1: The cast happens before the division, so
totalbecomes 47.0. Then47.0 / 6is adoubledivision: about 7.8333. - Step 2: Java prints the
doublewith all the digits it needs:7.833333333333333. - Step 3: For
rounded,avg + 0.5is about 8.3333. Casting tointtruncates it to 8. That's the correct rounded average, because 7.83 is closer to 8 than to 7.
Answer: It prints
7.833333333333333on the first line and8on the second. - Step 1: The cast happens before the division, so
- Example 2
Casting too late
This version moves the cast. What does it print now?
int total = 47; int count = 6; double avg = (double) (total / count); System.out.println(avg);Show the solutionHide the solution
- Step 1: The parentheses make
total / counthappen first. Both areints, so47 / 6is7, and the remainder is thrown away. - Step 2: Only then is 7 cast to a
double, which gives7.0. The cast can't bring back a decimal part that was already lost.
Answer: It prints
7.0. To get the exact average, cast one operand before dividing, as in(double) total / count. - Step 1: The parentheses make
Common mistakes
- Thinking
(int)rounds. It always truncates:(int) 9.99is 9. Add 0.5 first if you want to round a non-negative value. - Casting the result of an integer division and expecting the decimal back.
(double) (a / b)is too late; write(double) a / b. - Expecting an error when an
intgoes pastInteger.MAX_VALUE. Java silently wraps around to a negative number. - Comparing
doubleresults as if they were exact. Round-off means0.1 + 0.2isn't exactly0.3.
On the exam
- Expect questions that put a cast in different places and ask for the value. Apply the cast to the single value right after it, then follow precedence.
- If a free-response question asks for an average as a
double, cast one operand before dividing; integer division there is a common way to lose a point.
Connected topics
Videos
Check yourself
4 questions on 1.5 Casting and Range of Variables. Pick an answer to see if you got it, and why.
Consider the following code segment.double a = 7.9;
double b = 2.5;
System.out.println((int) a + (int) b);
System.out.println((int) (a + b));What is printed as a result of executing the code segment?
The method roundIt is intended to return its parameter rounded to the nearest whole number. For example, roundIt(2.5) should return 3 and roundIt(2.4) should return 2./** Precondition: x >= 0 */
public static int roundIt(double x)
{
return /* missing expression */;
}Which of the following can replace /* missing expression */ so that the method works as intended?
Consider the following code segment.int big = Integer.MAX_VALUE;
big = big + 1;
System.out.println(big == Integer.MIN_VALUE);What is printed as a result of executing the code segment?
Consider the following code segment.double sum = 0.1 + 0.2;
System.out.println(sum == 0.3);What is printed as a result of executing the code segment?
0 of 4 answered