[Java] 연산자

Java 입문 — 연산자

김영한의 자바 입문 강의 내용을 정리한 글이다.

1. 연산자 개요

+, -, *, /와 같이 계산을 수행하는 기호를 연산자(operator)라 한다. 연산자가 작용하는 대상은 피연산자(operand)다.

3 + 4 // 연산자: + 피연산자: 3, 4 a + b // 연산자: + 피연산자: a, b

자바가 제공하는 연산자를 분류하면 다음과 같다.

분류연산자
산술+, -, *, /, %
증감++, --
비교==, !=, >, <, >=, <=
논리&&, ||, !
대입=, +=, -=, *=, /=, %=
삼항? :

2. 산술 연산자

산술 연산자는 숫자를 계산하는 데 사용된다. +(더하기), -(빼기), *(곱하기), /(나누기), %(나머지) 다섯 가지다.

int a = 5; int b = 2; int sum = a + b; // 7 int diff = a - b; // 3 int multi = a * b; // 10 int div = a / b; // 2 (소수점 버림) int mod = a % b; // 1

정수 나눗셈과 소수점 버림

5 / 2의 수학적 결과는 2.5지만, 자바에서 int끼리 나누면 결과도 int다. 소수점 이하는 버림(truncation)으로 처리된다. 반올림이 아니라 0 방향으로 잘라낸다는 점이 중요하다.

System.out.println(7 / 2); // 3 (수학적으로는 3.5) System.out.println(-7 / 2); // -3 (수학적으로는 -3.5, 0 방향으로 절사)

음수에서도 절댓값이 작아지는 방향으로 잘린다. 이것은 수학적 바닥 나눗셈(floor division)과 다르다. 실수 결과가 필요할 때는 한 쪽을 double로 캐스팅한다.

double result = (double) 7 / 2; // 3.5
int / int → int (소수점 버림) 7 / 2 3 소수점 버림 double / int → double (소수점 유지) (double)7 / 2

나머지 연산자 %

나머지 연산자는 나눗셈 후 남은 값을 돌려준다. 5 % 2는 몫 2, 나머지 1이므로 결과가 1이다. 실무와 알고리즘에서 자주 쓰이는 대표적인 용도는 다음과 같다.

  • 홀짝 판별: n % 2 == 0이면 짝수, n % 2 != 0이면 홀수
  • 순환 인덱스: 배열 끝에 도달하면 처음으로 돌아오도록 index % length
  • 자릿수 분리: n % 10으로 마지막 자릿수 추출
int n = 17; System.out.println(n % 2 == 0 ? "짝수" : "홀수"); // 홀수 System.out.println(n % 10); // 7 (마지막 자리)

0으로 나누기

정수를 0으로 나누면 ArithmeticException: / by zero 예외가 발생하고 프로그램이 종료된다. 수학적으로도 정의되지 않는 연산이다.

Exception in thread "main" java.lang.ArithmeticException: / by zero

3. 문자열 더하기

자바는 문자열(String)에도 + 연산자를 사용할 수 있다. 두 문자열을 이어 붙이는 연결(concatenation) 연산이다.

String result1 = "hello " + "world"; // "hello world" String s1 = "string1"; String s2 = "string2"; String result2 = s1 + s2; // "string1string2"

문자열과 숫자를 더하면 숫자가 문자열로 자동 변환된 뒤 연결된다.

String result3 = "a + b = " + 10; // "a + b = 10" int num = 20; String str = "a + b = "; String result4 = str + num; // "a + b = 20"

계산 과정을 단계별로 따라가면 이렇다.

"a + b = " + 10(int) "a + b = " + "10" // int → String 자동 변환 "a + b = 10" // 문자열 연결

String에 어떤 타입을 더해도 그 타입을 문자열로 변환한 뒤 연결한다. 이것이 자바의 규칙이다.


4. 연산자 우선순위

수학에서 1 + 2 * 3의 결과는 7이다. 곱셈이 덧셈보다 우선순위가 높기 때문이다. 자바도 동일한 규칙을 따른다.

int sum1 = 1 + 2 * 3; // 7 (곱셈 먼저) int sum2 = (1 + 2) * 3; // 9 (괄호 먼저) int sum3 = 2 * 2 + 3 * 3; // 13 = (2*2) + (3*3) = 4 + 9 int sum4 = (2 * 2) + (3 * 3); // 13 (sum3과 동일, 명시적 표현)

자바 연산자 우선순위를 높은 순서부터 정리하면 다음과 같다.

순위분류연산자
1괄호()
2단항++, --, !, ~, (type)
3산술 (곱·나눗셈)*, /, %
4산술 (덧·뺄셈)+, -
5Shift<<, >>, >>>
6비교<, <=, >, >=, instanceof
7등식==, !=
8비트&, ^, |
9논리&&, ||
10삼항? :
11대입=, +=, -=, *=, /=, %=

실무 접근법

실무 개발자들은 우선순위 표를 외우지 않는다. 두 가지 원칙만 따른다.

  1. 상식 수준에서 판단한다. *+보다 우선이라는 것은 수학 상식이다. 대입 연산자 =가 가장 낮다는 것도 자연스럽다.
  2. 애매하면 괄호를 쓴다. 코드를 읽는 사람이 우선순위를 고민해야 한다면, 괄호로 의도를 명시하는 것이 맞다.
// 의도가 불분명한 코드 int x = a + b * c - d / e; // 의도가 명확한 코드 int x = (a + (b * c)) - (d / e);

코드는 짧을수록 좋은 것이 아니다. 읽는 사람이 이해하기 쉬울수록 좋다.


5. 증감 연산자

증감 연산자는 변수의 값을 1씩 증가(++)하거나 감소(--)시키는 단축 표현이다. 루프 카운터처럼 값을 1씩 올리는 상황이 프로그래밍에서 매우 자주 등장하기 때문에 이런 편의 문법을 제공한다.

int a = 0; a = a + 1; // 기존 방식: a = 1 ++a; // 동일한 효과: a = 2 a++; // 동일한 효과: a = 3

전위(Prefix) vs 후위(Postfix)

증감 연산자를 다른 연산과 함께 쓸 때 위치가 결과에 영향을 미친다.

  • ++a 전위: 증감을 먼저 수행한 뒤 나머지 연산
  • a++ 후위: 나머지 연산을 먼저 수행한 뒤 증감
전위(++a): 증가 먼저, 대입 나중 a 1 → ++a 실행 → a 2 → b에 대입 → b 2 a=2, b=2 후위(a++): 대입 먼저, 증가 나중 a 1 → b에 대입 → b 1 → a++ 실행 → a 2 a=2, b=1 b = ++a → a 먼저 증가 후 b에 대입 → a=2, b=2 b = a++ → b에 대입 후 a 증가 → a=2, b=1
int a = 1; int b = 0; b = ++a; // a를 먼저 2로 증가 → b에 2 대입 → a=2, b=2 System.out.println("a = " + a + ", b = " + b); // a = 2, b = 2 a = 1; b = 0; b = a++; // b에 현재 a(1) 대입 → a를 2로 증가 → a=2, b=1 System.out.println("a = " + a + ", b = " + b); // a = 2, b = 1

전위·후위 구분이 필요한 코드는 가독성을 해친다. 실무에서는 증감 연산자를 단독으로 사용하고, 대입과 섞는 패턴은 피하는 것이 권장된다.


6. 비교 연산자

비교 연산자는 두 값을 비교해 true 또는 false를 반환한다. 조건문에서 가장 많이 사용된다.

연산자의미예시결과
==같다2 == 3false
!=다르다2 != 3true
>크다2 > 3false
<작다2 < 3true
>=크거나 같다3 >= 3true
<=작거나 같다2 <= 3true
int a = 2; int b = 3; System.out.println(a == b); // false System.out.println(a != b); // true System.out.println(a > b); // false System.out.println(a < b); // true System.out.println(a >= b); // false System.out.println(a <= b); // true boolean result = a == b; // false를 변수에 저장

===는 전혀 다르다. =는 값을 저장하는 대입 연산자, ==는 두 값이 같은지 확인하는 비교 연산자다.

문자열 비교

문자열을 비교할 때는 == 대신 .equals() 메서드를 사용해야 한다. ==로 문자열을 비교하면 값이 아닌 객체의 주소를 비교하게 되어 기대와 다른 결과가 나올 수 있다. String이 참조 타입이기 때문이다.

String str1 = "문자열1"; String str2 = "문자열2"; boolean result1 = "hello".equals("hello"); // true boolean result2 = str1.equals("문자열1"); // true boolean result3 = str1.equals(str2); // false

7. 논리 연산자

논리 연산자는 boolean 값을 조합하는 데 사용된다.

연산자의미설명
&&AND (그리고)둘 다 true일 때만 true
||OR (또는)하나라도 true이면 true
!NOT (부정)truefalse로, falsetrue
&& (AND) 진리표 A B A && B true true true true false false false false false || (OR) 진리표 A B A || B true true true true false true false false false
System.out.println(true && true); // true System.out.println(true && false); // false System.out.println(false && false); // false System.out.println(true || true); // true System.out.println(true || false); // true System.out.println(false || false); // false System.out.println(!true); // false System.out.println(!false); // true

논리 연산자 활용

변수 a가 10보다 크고 20보다 작은지 확인하는 코드다.

int a = 15; boolean result = a > 10 && a < 20; // true // 범위 표현 — 가독성 있는 형태 boolean result2 = 10 < a && a < 20; // 동일한 결과

단락 평가 (Short-Circuit Evaluation)

&&||는 단락 평가를 수행한다. 첫 번째 피연산자만으로 결과가 확정되면 두 번째 피연산자를 아예 평가하지 않는다.

  • &&: 첫 번째가 false이면 두 번째를 보지 않는다. (어차피 결과가 false)
  • ||: 첫 번째가 true이면 두 번째를 보지 않는다. (어차피 결과가 true)
&& 단락 평가: 첫 번째가 false이면 두 번째는 평가하지 않음 false && 평가 안 함 false || 단락 평가: 첫 번째가 true이면 두 번째는 평가하지 않음 true || 평가 안 함 true

이 성질은 null 체크와 함께 자주 활용된다. snull이면 s.equals()를 호출하지 않으므로 NullPointerException이 발생하지 않는다.

String s = null; if (s != null && s.equals("hello")) { System.out.println("일치"); } // s가 null이므로 첫 번째 조건이 false → 두 번째 조건 평가 안 함 → 안전

8. 대입 연산자

대입 연산자 =는 오른쪽 값을 왼쪽 변수에 저장한다.

복합 대입 연산자

산술 연산과 대입을 한 번에 축약한 것이 복합 대입 연산자다.

연산자풀어 쓴 형태
i += 3i = i + 3
i -= 2i = i - 2
i *= 4i = i * 4
i /= 3i = i / 3
i %= 5i = i % 5
int a = 5; a += 3; // 8 (5 + 3) a -= 2; // 6 (8 - 2) a *= 4; // 24 (6 * 4) a /= 3; // 8 (24 / 3) a %= 5; // 3 (8 % 5) System.out.println(a); // 3

복합 대입 연산자는 가독성 외에 한 가지 중요한 특성이 있다. 연산 결과를 왼쪽 변수 타입으로 자동 캐스팅한다.

byte b = 10; b += 5; // 컴파일 가능 (자동 캐스팅) b = b + 5; // 컴파일 오류: int → byte 명시적 캐스팅 필요

b + 5는 자바 내부에서 int로 계산된 뒤 다시 byte에 넣으려 하기 때문에 오류가 발생한다. +=는 이 과정을 자동으로 처리한다.


9. 삼항 연산자

삼항 연산자는 조건에 따라 두 값 중 하나를 선택하는 연산자다. 피연산자가 세 개라서 삼항(三項)이다.

조건식 ? 참일 때 값 : 거짓일 때 값
int a = 10; int b = 20; int max = a > b ? a : b; // 20 (b가 더 크므로)

if-else로 풀어 쓰면 다음과 같다.

int max; if (a > b) { max = a; } else { max = b; }

단순한 조건 분기에서 삼항 연산자를 쓰면 코드가 짧고 명확해진다. 단, 조건이 복잡하거나 중첩이 필요한 경우에는 if-else가 훨씬 읽기 좋다.

// 중첩 삼항은 읽기 어렵다 — 실무에서 지양 String grade = score >= 90 ? "A" : score >= 80 ? "B" : score >= 70 ? "C" : "F"; // if-else가 더 명확하다 String grade; if (score >= 90) grade = "A"; else if (score >= 80) grade = "B"; else if (score >= 70) grade = "C"; else grade = "F";

10. 연습 — int와 평균

세 정수의 합과 평균을 구하는 코드다. int끼리 나누면 소수점이 버려진다는 점을 확인할 수 있다.

int num1 = 10; int num2 = 20; int num3 = 30; int sum = num1 + num2 + num3; // 60 int average = sum / 3; // 20 (소수점 버림) System.out.println(sum); // 60 System.out.println(average); // 20

double로 바꾸면 소수점이 살아난다.

double val1 = 1.5; double val2 = 2.5; double val3 = 3.5; double sum = val1 + val2 + val3; // 7.5 double avg = sum / 3; // 2.5 System.out.println(sum); // 7.5 System.out.println(avg); // 2.5

'Study > Java' 카테고리의 다른 글

[Java] 스코프, 형변환  (0) 2026.04.04
[Java] 반복문  (0) 2026.04.04
[Java] 조건문  (0) 2026.04.04
[Java] 변수  (1) 2026.04.03
[Java] Java란?  (0) 2026.04.03