본문 바로가기
Java/Java

제어문) switch문, switch문 fall-through

by 박채니 2022. 3. 4.
SMALL

안녕하세요, 코린이의 코딩 학습기 채니 입니다.

 

개인 포스팅용으로 내용에 오류 및 잘못된 정보가 있을 수 있습니다.


선택 제어문 2가지 중 하나인 switch문에 대해서 알아보겠습니다.


☞ switch문

- 값으로 처리 될 수 있는 변수 또는 계산식을 검사

- 해당하는 case문으로 점프!

- break를 만나서 switch문 탈출

- 해당하는 값이 없다면 switch문을 빠져나가거나 default 구문 실행

//기본 구문
switch(점프위치변수) {
	case 위치값 1: 실행구문; break;
	case 위치값 2: 실행구문; break;
	...
	default: 실행구문;
}

 

public void test1() {
	char ch = 'c';
		
	switch(ch) {
	case 'a': System.out.println("ch는 a입니다."); break;
	case 'b': System.out.println("ch는 b입니다."); break;
	case 'c': System.out.println("ch는 c입니다."); break;
	}
    System.out.println("끝!")
}

@콘솔출력값
ch는 c입니다.

// ch = 'x'입력 시 콘솔출력값
끝!

(점프위치변수) 에 올 수 있는 허용 범위는 byte, short, char, int, String, enum 이며 그 이외는 올 수 없습니다.

또한, 일치 값이 없다면 (ch = 'x') switch 문을 빠져나가게 되어 "끝!"을 출력하게 됩니다.

 

if문의 else처럼 case문도 default구문을 입력하여 일치하는 것이 없다면 default구문을 출력하게 할 수 있습니다.

char ch = 'x';
		
switch(ch) {
case 'a': System.out.println("ch는 a입니다."); break;
case 'b': System.out.println("ch는 b입니다."); break;
case 'c': System.out.println("ch는 c입니다."); break;
default: System.out.println("일치하는 값이 없습니다.");

@콘솔출력값
일치하는 값이 없습니다.

 

switch문 이용하여 메뉴 선택하는 구문 만들기

public void test2() {
	String menu = "좋아하는 과일을 선택하세요~\n"
				+ "1. 사과	1000원\n"
				+ "2. 바나나	1300원\n"
				+ "3. 오렌지	2000원\n"
				+ "4. 아보카도 3500원\n"
				+ "선택 : ";
	System.out.print(menu);
		
	Scanner sc = new Scanner(System.in);
		
	int choice = sc.nextInt();
	int price = 0;
		
	switch(choice) {
	case 1: price = 1000; break;
	case 2: price = 1300; break;
	case 3: price = 2000; break;
	case 4: price = 3500; break;
	default: System.out.println("잘못 입력하셨습니다. 종료합니다."); return;
	}
		
	System.out.println("가격은 " + price + "원입니다.");
}

@콘솔출력값
좋아하는 과일을 선택하세요~
1. 사과	1000원
2. 바나나	1300원
3. 오렌지	2000원
4. 아보카도 3500원
선택 : 3
가격은 2000원입니다.

//1~4 아닌 값 입력 시
좋아하는 과일을 선택하세요~
1. 사과	1000원
2. 바나나	1300원
3. 오렌지	2000원
4. 아보카도 3500원
선택 : 5
잘못 입력하셨습니다. 종료합니다.

return; 은 메소드를 호출한 호출부로 돌아가게 합니다. return;이 없으면 아래의 println문도 같이 출력됩니다.

 

switch문 이용하여 메뉴 선택하는 구문 만들기2

public void test3() {
		String menu = "=====================\n"
				+ "1. 순대국 ------ 8000원\n"
				+ "2. 김치찌개 ----- 7000원\n"
				+ "3. 된장찌개 ----- 7500원\n"
				+ "---------------------\n"
				+ "번호 선택 : ";
	System.out.print(menu);
		
	Scanner sc = new Scanner(System.in);
	String choice = sc.next();	//형변환 오류 없도록 String으로 받음
     //int로 받으면 정수형으로 변환하여 반환
		
	String userMenu = "";
	int price = 0;
		
	switch(choice) {
	case "1": price = 8000; userMenu = "순대국"; break;
	case "2": price = 7000; userMenu = "김치찌개"; break;
	case "3": price = 7500; userMenu = "된장찌개"; break;
	default: System.out.println("잘못 선택하셨습니다. 종료합니다."); return;
	}
		
	System.out.printf("%s을(를) 선택하셨습니다. 결제하실 금액은 %d원입니다.", userMenu, price);
}

@콘솔출력값
=====================
1. 순대국 ------ 8000원
2. 김치찌개 ----- 7000원
3. 된장찌개 ----- 7500원
---------------------
번호 선택 : 3
된장찌개을(를) 선택하셨습니다. 결제하실 금액은 7500원입니다.

//1~3아닌 값 입력 시
=====================
1. 순대국 ------ 8000원
2. 김치찌개 ----- 7000원
3. 된장찌개 ----- 7500원
---------------------
번호 선택 : 4
잘못 선택하셨습니다. 종료합니다.

※ Scanner는 받는 자료형에 따라서 동일한 자료형으로 변환 후 반환합니다.

따라서 int 형으로 scanner를 받으면 int로 자동 형변환 후 반환 됩니다. 

int형으로 받았다가 사용자가 "ㄱㄷ" 등 숫자가 아닌 값을 잘못 입력하였을 때 input 에러가 납니다.

에러를 최소화 하기 위하여 String으로 받아주었습니다. (String으로 받고 "ㄱㄷ"등 잘못 입력한다면 default문이 출력되겠죠?)

 

case문 뒤에 break를 사용하는 이유는?

- break는 if문을 제외한 가장 가까운 중괄호({})를 탈출

- if문과 다르게 switch문은 해당하는 case문으로 단순 이동 시키는 것이므로 그 다음부터는 원래 프로그램 실행 순서대로 1줄씩 실행

따라서 break문이 없으면 해당하는 case문 이동 후 관계없는 아래 case문까지 다 출력이 되는 것이죠.

 

public void test1() {
	char ch = 'b';
		
	switch(ch) {
	case 'a': System.out.println("ch는 a입니다."); 
	case 'b': System.out.println("ch는 b입니다."); 
	case 'c': System.out.println("ch는 c입니다."); 
	default: System.out.println("일치하는 값이 없습니다.");
}

@콘솔출력값
ch는 b입니다.
ch는 c입니다.
일치하는 값이 없습니다.

이전에 실행했던 test1 메소드에서 break만 빼보았더니 결과는 완전히 다르게 나왔습니다.

case 'b'로 이동 후 break가 없으므로 switch구문이 끝날 때까지 다 실행해버린 것입니다. 이러한 이유로 break를 사용합니다.

 

하지만 의도적으로 break문을 사용하지 않을 때도 있습니다.

 

☞ switch문 fall-through

	/**
	 * 90 ~ 100 : A
	 * 80 ~ 89 : B
	 * 70 ~ 79 : C
	 * 60 ~ 69 : D
	 * ~ 59 : F
	*/

public void test4() {
	Scanner sc = new Scanner(System.in);
	System.out.print("점수 입력 : ");
		
	int score = sc.nextInt();
	char grade ='F';
		
	switch(score / 10) {
	case 10:
	case 9: grade = 'A'; break;
	case 8: grade = 'B'; break;
	case 7: grade = 'C'; break;
	case 6: grade = 'D'; break;
	}
		
	System.out.println("학점 : " + grade);
}

@콘솔출력값
점수 입력 : 95
학점 : A

위와 같이 점수에 따라 학점을 출력해주는 switch구문을 만들어주었으며, 10 (100) ~ 9 (90) 까지는 'A'등급이기 때문에 만일 점수가 10 (100)이여도 'A', 9 (90점대)이여도 'A'입니다.

따라서 case 10 :에 break 문을 제거하여 10~9까지는 'A'가 출력되게끔 만들어줄 수 있었습니다.

 

각 등급 별 선물 출력하기

/**
	 * gold		: 스마트tv, 전자렌지, 전기다리미
	 * silver	: 전자렌지, 전기다리미
	 * bronze	: 전기다리미
	 */
public void test5() {
	Scanner sc = new Scanner(System.in);
	System.out.print("> 회원 등급을 선택하세요 (a.골드 b.실버 c.브론즈) : ");
	
	String grade = sc.next();
	String present = "";
		
	switch(grade) {
	case "a": present+="스마트tv, ";
	case "b": present+="전자렌지, ";
	case "c": present+="전기다리미"; break;
	}
	System.out.println(present);
}

@콘솔출력값
> 회원 등급을 선택하세요 (a.골드 b.실버 c.브론즈) : a
스마트tv, 전자렌지, 전기다리미

fall-through 성질을 이용하여 위와 같이 간단하게 코드를 짜볼 수 있었습니다.

LIST