Concepts / Arithmetic Operators in Java

Arithmetic Operators in Java

Syntax is the form a program must take, and the source stresses that knowing syntax is only part of being a successful programmer.

  • Programming

Predicting Output Before Reading Further

Suppose you have written a Java program. You typed it carefully, the compiler accepted it, and it ran without complaint. Does that mean the program is finished? Not necessarily. A program can be written in valid form and still print a result you did not want. Nothing about a program's shape tells you whether the number it prints is the number you needed.

Before reading any explanation, try to predict what the following statement prints. It divides one integer by another and displays the result. The question is not whether the line is valid. The question is what Java means by dividing one integer by another.

java

What do you think happens?

What do you think this statement prints?

  • 3.5

  • 3

  • 4

  • 3.0

Reveal answer
Answer:

3

Both operands are integers, so Java performs integer division. The fractional part is discarded, leaving 3. The result is not 3.5 because 3.5 would require a real-number result, and no real operand is present.

If your prediction was 3.5, you applied ordinary mathematics. If you predicted 3, you applied the rules of the language. This article is about that difference. The rest of the article first separates form from meaning, then looks at how a wrong meaning can hide behind a program that looks reasonable, and finally works through each arithmetic operator and its rules.

Syntax Versus Semantics

Definition

Syntax is the form a program must take in order to be written in a language at all. It is the set of spelling and structure rules the compiler checks.

Definition

Semantics is the set of rules that determine the meaning of a program written in that language. It answers the question of what the program does once it runs.

Getting the form right is necessary, but it is not sufficient. A program has to mean the right thing, and the meaning is governed by its own rules. A useful way to hold the two ideas apart is to ask two different questions about the same code. The first question is whether the text is written in a form the language accepts. The second is what the program does when it runs, and whether that behavior matches what you wanted. A program can pass the first check and fail the second, and only the second check tells you whether you have solved the problem.

Key point

Correctness is judged against intent, not against whether the code compiles. A semantically correct program is one that does what you want it to do.

Tracing a Valid Program With a Wrong Result

Consider a program meant to compute the average of two whole numbers, 5 and 2. The intended answer is 3.5. The program below is valid Java and uses the division operator in a natural-looking way. Read it, then trace what the division actually produces before looking at the output.

Code walkthrough
public class Average {
    public static void main(String[] args) {
        int a = 5;
        int b = 2;
        int average = (a + b) / 2;
        System.out.println(average);
    }
}
  1. 1
    Two int variables hold 5 and 2.
  2. 2
    The expression a + b produces the int value 7.
  3. 3
    Dividing the int 7 by the int 2 uses integer division, which discards the fractional part and leaves 3.
  4. 4
    The program prints 3. It compiled and ran without error, but 3 is not the intended 3.5. The error is in the meaning of the division, not in the form of the code.
  • a and b are both int variables
  • a + b evaluates to 7, an int
  • 7 / 2 is integer division, so the result is 3
Output
3

The Basic Arithmetic Operators

Most arithmetic operators combine two values, called operands. The operators look familiar from mathematics, but each one is defined by Java's rules, and the types of the operands affect the result. The table lists the operators this article focuses on.

OperatorOperationExampleResult
+Addition, or concatenation when one side is a String2 + 35
-Subtraction9 - 45
*Multiplication3 * 412
/Division; integer division when both operands are integers7 / 23
%Remainder: what is left after division7 % 21

Java's basic binary arithmetic operators. Examples are generated for illustration; the division and remainder results follow the source's rules.

Division With Integers Versus Real Numbers

Division follows the type of its operands. Two integer operands produce an integer result, even when ordinary mathematical division would include a fractional part. Integer division discards that fractional part. If at least one operand is a real number, Java converts the other operand to a real number and produces a real-number result.

java
Output
3
3.5
Notes on the code
  • 7 and 2 are both int, so the division is integer division and the result is 3
  • 7.0 is a real number, so the division is real-number division and the result is 3.5
7 / 2int divided by int7.0 / 2real divided by intInteger resultfractional part discardedReal result2 converted to 2.03printed value3.5printed valueinteger rulepromotion
Why does 7 / 2 produce 3 while 7.0 / 2 produces 3.5? The type of the operands decides the type of the result.

The same symbol produces two different kinds of result. Once you see the division as a question about types, the 3 versus 3.5 difference stops being surprising.

Type Conversion When Operands Differ

When Java evaluates an arithmetic expression, it must determine both what operation to perform and what types the operands should have while performing it. Suppose an expression combines values whose types differ. Before carrying out the operation, Java converts one value so that the two operands match. This automatic adjustment is called type conversion.

In the expression 37.4 + 10, the integer 10 is converted to the real number 10.0. Java then evaluates the operation using 37.4 and 10.0. The integer is the operand that changes; the real number is left alone, and the result is a real number.

37.4double operandAdditionboth operands now real47.4real-number result10int operand10.0int converted to realunchangedconverted
When an int and a double meet in one expression, which operand is converted, in which direction, and what type does the result have?
Key point

The conversion goes in one direction: the integer is converted to a real number, not the other way round. Because the operands now match, the type of the result is real, and that is why the fractional part survives.

The Remainder Operator

The percent sign, %, does not mean percentage in this context. The remainder operator gives what remains after one number is divided by another. It is a different question from division: division asks how many times one number fits into another, and the remainder asks what is left over.

java
Output
1
77
2
Notes on the code
  • 7 divided by 2 leaves 1
  • 34577 divided by 100 leaves 77, the last two digits
  • 50 divided by 8 leaves 2

The remainder is especially useful for checking whether a value divides evenly. For example, a number n is divisible by 2 exactly when n % 2 gives 0. The examples above use integer operands, which is the case the source covers.

Unary Operators and Their Effect

Most arithmetic operators combine two values. Unary operators are different because they act on one operand. Java provides unary minus and unary plus.

Formula

Unary minus changes a number to its negative. Unary plus is also available, but +X leaves the value of X unchanged. Unary plus therefore does not change the value of the operand it is applied to.

java
Output
-6
6
6
Notes on the code
  • unary minus produces the negative of x
  • unary plus leaves the value of x unchanged
  • x itself still holds 6

The Plus Operator: Addition or Concatenation

The plus operator has two roles in Java. With numbers on both sides, + performs arithmetic addition. When one side of the operation is a String, + concatenates the value onto that text instead. The other value is automatically converted to String for this combination.

Evaluate a + bleft to rightIs either operand aString?check operand typesNumeric additionno String involvedConcatenate textother value converted toStringnoyes
Given the operand types and the left-to-right order of evaluation, when does + add numbers and when does it join text?
java
Output
3x
x12
Notes on the code
  • 1 + 2 is evaluated first, both operands are numbers, so it adds to 3; then 3 + x joins text
  • "x" + 1 is evaluated first, the String side forces concatenation, giving x1; then x1 + 2 gives x12

The two lines contain the same numbers and the same operator, yet print different results. The difference is the order of evaluation. Java works through the + operations from left to right, and the type of the left-hand result decides whether the next + adds or joins text.

Mistakes That Hide Behind Valid Code

  • Common mistake

    Expecting integer division to keep the fractional part

    What it looks like
    System.out.println(7 / 2); expected to print 3.5
    Why it fails

    Two int operands produce an int result, so the fractional part is discarded and the output is 3.

    Do this instead

    Make at least one operand a real number, such as 7.0 / 2, to get 3.5.

  • Common mistake

    Dividing before adding when averaging

    What it looks like
    int average = a + b / 2; intended as the average of a and b
    Why it fails

    Division binds before addition, so only b is divided by 2.

    Do this instead

    Use parentheses to state the intent: (a + b) / 2, with a real operand if the fraction matters.

  • Common mistake

    Assuming + always adds numbers

    What it looks like
    System.out.println(1 + 2 + "x"); expected to print x12
    Why it fails

    1 + 2 is evaluated first as numeric addition, producing 3, and only then is the text joined.

    Do this instead

    Read the expression left to right and check the type of each intermediate result.

  • Common mistake

    Expecting unary plus to change a value

    What it looks like
    System.out.println(+x); expected to show a different number from x
    Why it fails

    Unary plus leaves the value of its operand unchanged.

    Do this instead

    Use unary minus when you need the negative of a value.

Checking Behavior Against Intent

Best practice

Before you trust a program, decide in advance what result it should produce for a chosen input. Then run it and compare. A mismatch tells you that something about the meaning is off, even when every line is valid. For the averaging example, choosing inputs 5 and 2 and writing down 3.5 beforehand would have exposed the integer-division error immediately.

Practice: Predict Before You Run

MEDIUM

For each statement, predict the printed value using the meaning rules, then check. (a) System.out.println(9 / 4); (b) System.out.println(9.0 / 4); (c) System.out.println(9 % 4); (d) System.out.println("n = " + 9 / 4); (e) System.out.println(2 + 3 + "y").

Hints
  • Ask first whether each division has two int operands or a real operand.
  • For (d), division happens before the + that joins the text, because division binds before addition.
  • For (e), evaluate the numeric additions from left to right before the text is joined.

Key Takeaways

  • Syntax is the form a program must take, while semantics are the rules that determine what the program means; a program can compile and still produce a result the programmer did not intend.
  • Division of two integers produces an integer result that discards the fractional part; if one operand is a real number, the other is converted and the result is real.
  • The remainder operator % gives what is left after division, and unary minus gives the negative of its operand while unary plus leaves the value unchanged.
  • The plus operator adds numbers when neither side is a String and concatenates text when one side is a String, evaluated left to right.
  • Check a program against the result you intended by predicting its output for a chosen input before running it.