목표

  • 자바가 제공하는 다양한 연산자를 학습하세요

학습할것

  • 산술 연산자
  • 비트 연산자
  • 관계 연산자
  • 논리 연산자
  • instanceof
  • assignment(=) operator
  • 화살표(->) 연산자
  • 3항 연산자
  • 연산자 우선 순위
  • (optional) Java 13. switch 연산자

산술 연산자

  • 산술연산자는 사칙연산자 ( + , - , * , / ) 4개와 나머지 연산자 ( % ) 로 이루어져 있다.

  • 사칙 연산자

    • 피 연산자가 정수 일 경우 0 으로 나눌수 없다.

    • 피 연산자가 같을 경우 결과는 피연산자와 같고

    • 피 연산자가 다를 경우 ( 정수 + 실수 ) 조합일 때 결과는 실수가 된다.

    • 피 연산자가 다를 경우에는 좀더 범위가 넓은쪽을 결과의 타입으로 쓴다.

    • 연산자 결과의 최소 타입은 int형이다.

      byte a = 1; byte b = 1; byte c = a+b; // 에러발생 provided는 int형 인데 byte에 담으려 했기 때문 byte c = (byte)(a+b); // 명시적 형변환할 경우 에러안남
      • byte+byte로 더해서 byte에 담으려 하면 에러가 난다.
        • 결과는 int로 나오는데 int ( 4byte)보다 더작은 byte에 담으려 했기 때문
        • 이때는 명시적으로 형변환을 시켜줘야 한다.
        • 하지만 큰 타입에서 작은 타입으로 변환해서 데이터를 넣을 경우
        • 값이 작은 타입의 데이터 범위를 넘을 경우 데이터 손실이 일어난다.
    int aa = 1000000; int bb = 1000000; long cc = aa*bb; // result -727379968
    • 같은 타입 피연산자의 연산결과 합이 타입의 허용 값을 넘어서 결과가 나온다면
    • 더 높은값을 담을수 있는 타입에 저장할 때 이 타입의 형태로 저장되는게 아닌 피연산자 타입의 연산결과의 합이 담긴다.
    • 그리고 연산 중 오버플로우가 일어난다면
    • 상위 타입에 저장한다고 해도 이미 오버플로우가 일어나서 오버플로우가 일어나기 전까지의 값만 저장가능하다.
  • 문자열 연산

char a = 'a'; char b = 'b'; char c = a+b; // 결과값은 Ã String a = "a"; String b = "b"; String c = a+b; final char a= 'a'; final char b = 'b'; char ccc = a+b; // 에러 안남

  • char의 문자열 연산은 해당문자의 유니코드 ( 정수 ) 로 바뀌어 저장되므로 정수간의 연산이된다.

  • 문자열 자체가 더해지는 것이 아닌 유니코드가 더해져서 char에 변수에 담는것이다.

  • 재밌게도 스트링은 따로 형변환을 안해도 되고 그자체로 더해진다.

    • 그 이유는 스트링은 리터럴이기 때문이다.
    • 리터럴 끼리의 합은 형변환을 안해도 된다.
      • 문자열 끼리만이 아닌 정수와 실수도 가능하다.
  • 리터럴 연산

    • 리터럴 연산은 컴파일시 컴파일러가 먼저 계산하고 리터럴간의 연산을 먼저 실행시킨다.
    • 그래서 형변환을 안해도 연산이 되는것이다.
    • 만약 리터럴이 아닐경우 도중에 값이 바뀔 위험이 있기에 컴파일러가 미리 연산을 하지 못한다 그래서 형변환이 필요한것이다.
  • 나머지 연산자

    • 왼쪽의 피 연산자를 오른쪽의 피연산자로 나누고 난 나머지 값을 결과로 리턴하는 연산자.
    • 나눗셈처럼 나누는 수 ( 오른쪽 피 연산자) 를 0으로 사용할수 없다.

비트 연산자

  • 피연산자를 비트단위로 논리 연산한다.

  • 피연산자를 이진수로 표현할 경우의 각 자리를 규칙에따라 연산하고 피연산자로 실수는 허용하지 않는다. 정수만 가능

  • 연산 규칙

    • | ( OR 연산자 )
      • 피연산자 중 한쪽의 값이 1이면 1로 값을 리턴한다 그 이외에는 0으로 리턴
    • & ( AND 연산자 )
      • 피연산자 양쪽이 모두 1이어야만 1로 값으로 리턴한다. 그이외에는 0으로 리턴
    • ^ ( XOR 연산자 )
      • 피연산자의 값이 서로 다를때만 1로 값을 리턴한다. 같을때는 0을 리턴한다.
  • 쉬프트 연산자 << >>

    • 피연산자의 각 자리 ( 2진수로 표현했을 때)를
    • 오른쪽 >> 또는 왼쪽 << 으로 이동한다고 해서 쉬프트 연산자 라고 불린다.
    • 예를 들어 " 8 << 2 " 는 왼쪽 피연산자인 10진수의 8의 2진수를 왼쪽으로 2자리 이동한다.
    10진수 8은 2진수로 '00001000' 8 << 2 는 10진수 8의 2진수를 왼쪽으로 2자리 이동시킨다 0 0 0 0 1 0 0 0 에서 왼쪽으로 2자리 이동되므로 가장 앞 2자리는 버려진다. 남은 값은 0 0 1 0 0 0 0 0 (10진수로 32) 빈자리는 0으로 채워진다. System.out.println((8 << 2)); // 결과값은 32
  • 비트전환 연산자 ~

    • 피연산자를 2진수로 표현했을때 0은 1로 , 1은 0으로 바꾼다.
    byte p = 10; System.out.println("~p = " + ~p); // 결과 -11 10은 이진수로 00000000000000000000000000001010이 된다. ~를 사용하여 0과 1이 뒤바뀌면 아래와 같이 -11의 이진수 값이 된다. -11은 이진수로 11111111111111111111111111110101이 된다.

관계 연산자

  • 두 연산자를 비교하는데 사용되는 연산자다.
  • 주로 조건문 과 반복문의 조건식에 사용된다.
  • 결과는 오직 true, false 단 두개뿐이다.

대소비교 연산자

  • 두 연산자의 값의 크기를 비교하는 연산자

  • 참 일 경우 true , 거짓이면 false를 리턴한다.

  • boolean형을 제외한 나머지 자료형에는 사용가능하나 참조형에는 사용할수 없다.

  • 4가지 종류가 존재한다.

      • 좌변이 크면 ture 아니면 false
    • <
      • 좌변이 작으면 true 아니면 false
    • =

      • 좌변이 크거나 같으면 true 아니면 false
    • <=
      • 좌변이 작거나 같으면 true 아니면 false

등가비교 연산자

  • 두 피연산자의 값이 같은지 또는 다른지를 비교하는 연산자

  • 대소비교 연산자와 다르게 기본형 , 참조형 , 모든 자료형에 사용 가능하다.

  • 기본형의 등가비교일 경우 저장되어있는 값이 같은지를 알수 있고

  • 참조형의 등가비교일 경우 저장되어있는 객체의 주소값을 비교한다.

  • 2가지 종류가 존재

    • ==
      • 두 값이 같으면 ture 아니면 false
    • !=
      • 두 값이 다르면 true 아니면 false

문자열의 비교

  • String으로 문자열을 비교할 경우에는 == 대신 equals를 사용 해야 한다.
  • ==로 비교하는 것은 참조주소를 비교한다는 것이기 때문에 만약 문자열이 같더라도
  • 참조주소가 다르면 다른것으로 간주하기 때문이다.
  • equals를 사용하면 문자열을 비교하기 때문에 문자열이 같으면 true를 반환한다.

논리 연산자

  • 2가지 조건으로 결합하여 참과 거짓을 구분한다.
    • && 와 ||

boolean a = true; boolean b = false; (a && a) // true (a || a) // true (a && b) // false (a || b) // true (b && b) // false (b || b) // false

  • 2가지 조건
    • && ( AND 결합 )
      • 피연산자 양쪽 모두 true 이어야 true를 리턴한다.
    • || ( OR 결합 )
      • 피연산자 중 한쪽 만 true면 true를 리턴 한다.

논리 부정 연산자

  • 피연산자가 true면 false로 false면 true로 결과를 바꿔서 리턴한다.

boolean a = true; boolean b = false; !a // false; !b // true;

instance of 연산자

  • 참조변수가 참조하고 있는 인스턴스의 실제 타입을 확인하는 연산자.
  • instanceOf 가 true 란 것은 그 타입일수도 있고 그 타입으로 형변환이 가능하다는 것이다.

void test (Car c) { if (c instanceOf SportsCar) { SportsCar sc = (SportsCar)c; } }

  • 위와 같이 사용할 경우 test 메소드의 Car c의 타입을 정확히 알수가 없다.
  • 진짜 car인지 아니면 car의 자손 클래스인지 정확히 알수가 없다.
  • 그렇기 떄문에 체크해서 사용한다.

assignment(=) operator

  • 대입 연산자

    • 변수와 같은 저장공간에 값 또는 수식의 연산결과를 저장하는데 사용
    • 오른쪽 피연산자의 값을 왼쪽 피연산자에 저장한다.
    • 대입 연산자의 왼쪽 피연산자를 lvalue ( left value ) 라고 하며
    • 오른쪽을 rvalue ( right value ) 라고 한다.
  • 복합 대입연산자

    • 다른 연산자와 결합하여 op= 와 같은 방식으로 사용가능하다.
    i = i+3; 과 같은 코드를 i +=3; 과 같이 사용 가능하다.

화살표 연산자

  • lambda를 표현식을 작성하기 위한 연산자다.

1. Interface k = new Interface() { @Override public void main() { } }; 2. Koy k = () -> { };

  • 위와 같이 인터페이스의 메소드가 1개일 경우 아래와같이 익명함수를 간단하게 람다식으로 변경할수 있다.

3항 연산자

  • 피연산자를 3개를 사용하는 연산자
  • 조건식과 결과 결과 로 이루어져 있으며 결과에 다시 3항연산자가 들어갈수도 있다.

int a = 1; int b = 2; int c = 3; boolean d = a < b ? true : false boolean d = a < b ? a < c ? true : false : false

연산자 우선순위

  • 식에 사용된 연산자가 둘 이상일 경우 연산자 우선순위에 의해 순서가 결정된다.
  • 곱셈과 나눗셈은 덧셈과 뺼셈보다 우선순위가 높다. ( 기초수학 )

x << 2 + 1 data & 0xFF == 0 x < 1 || x > 3 && x < 5

  • << 연산자는 덧셈 연산자보다 우선순위가 낮다.
  • & 연산자는 == 연산자보다 우선순위가 낮다.
  • &와 && 연산자는 |과 || 보다 우선순위가 높다.
  • and 와 or을 같이사용하는 경우에는 괄호를 사용해 우선순위를 명확하게 하는것이 좋다.

x + 3 > y - 2 x > 3 && x - 2 result = x + y * 3

  • 비교연산자는 산술 연산자보다 우선순위가 낮다

  • && 연산자는 비교 연산자보다 순위가 낮다.
  • 대입연산자는 연산자중에서 우선순위가 제일 낮다.

우선순위 결론

  • 산술 > 비교 > 논리 > 대입 의 순위이며

  • 대입은 제일 마지막에 수행된다.

  • 단항 > 이항 > 삼항

  • 단항 연산자의 우선순위가 이항 연산자보다 높다.

  • 단항 연산자와 대입연산자를 제외한 모든 연산의 진행방향은 왼쪽에서 오른쪽이다.

Java 13 Switch Operator

  • preview 기능이므로 —enable-preview 옵션을 줘야 사용할수 있다.

  • : 대신 → 를 사용할 수 있다.

  • switch가 expression으로 사용될 수 있다.

    • 타입을 지정하고 변수를 할당할수 있게 되었다.
  • yeild 키워드가 추가 되었다.

    • return과 같이 사용가능.

switch (name) { case "KKK" -> System.out.println("이름이 KKK"); case "DDD" -> System.out.println("이름이 DDD"); } String result = switch (name) { case "KKK" -> "nameKKK"; case "DDD" -> "nameDDD"; }; String result = switch (name) { case "KKK" -> "nameKKK"; case "DDD" -> "nameDDD"; default -> { String a = "newname" yield a; } };

출처

https://johngrib.github.io/wiki/jdk13/#switch-expressions-preview

자바의정석

http://blog.kurien.co.kr/495

'백선생님 온라인스터디' 카테고리의 다른 글

6주차 상속  (0) 2021.01.10
4주차 - 제어문  (0) 2021.01.09
연산자  (0) 2020.11.28
스터디 2주차 - 자바 데이터타입, 변수 그리고 배열  (0) 2020.11.21
스터디 1주차 - JVM  (0) 2020.11.15

+ Recent posts