주어진 조건의 참(true) 또는 거짓(false) 여부에 따라 프로그램의 실행 흐름을 나누는 구문
비교 결과를 담은 bool 변수는 그대로 조건이 됨.
== true 를 붙일 필요가 없음.
using System;
int hp = 80;
int mp = 40;
bool canCast = hp > 0 && mp >= 30;
if (canCast)
{
Console.WriteLine("주문을 시전함");
}
if (!canCast)
{
Console.WriteLine("주문을 쓸 수 없음");
}
조건이 복잡할 때는 이렇게 이름 있는
bool 변수로 뽑아 두면
if 줄이 읽기 쉬워짐
using System;
int level = 12;
int stamina = 5;
bool hasKey = true;
// 조건을 그대로 늘어놓으면
if (level >= 10 && stamina > 0 && hasKey)
{
Console.WriteLine("문을 열 수 있음");
}
// 이름을 붙이면
bool isStrongEnough = level >= 10;
bool canMove = stamina > 0;
bool canOpenDoor = isStrongEnough && canMove && hasKey;
if (canOpenDoor)
{
Console.WriteLine("문을 열 수 있음");
}
실행 결과
문을 열 수 있음
문을 열 수 있음
생략하면 if 에 딸린 문장은 바로 다음 한 줄뿐임.
나중에 한 줄을 더 넣으면 그 줄은 조건과 무관하게 항상 실행됨.
using System;
int hp = 50;
if (hp <= 0)
Console.WriteLine("쓰러졌음");
Console.WriteLine("부활 대기 중"); // if 에 딸리지 않음
Console.WriteLine("--- 끝 ---");
실행 결과
부활 대기 중
--- 끝 ---
들여쓰기가 맞춰져 있어서 두 줄 모두 if에 속한 것처럼 보이지만, 실제로는 두 번째 줄이 조건과 무관하게 실행됨. 중괄호를 쓰면 이런 일이 생기지 않음.
정수를 2로 나눈 나머지가 0이면 짝수이고, 0이 아니면 홀수임.
음수 홀수의 나머지는 -1이므로 1과 같은지만 검사하면 안 됨.
using System;
int number = 15;
if (number % 2 == 0)
{
Console.WriteLine($"{number} 은 짝수");
}
else
{
Console.WriteLine($"{number} 은 홀수");
}
실행 결과
15 은 홀수
여러 수를 확인하면 나머지가 어떻게 갈리는지 보임.
using System;
int a = 8;
int b = 13;
int c = 0;
int d = -7;
Console.WriteLine($"{a} % 2 = {a % 2} → {(a % 2 == 0 ? "짝수" : "홀수")}");
Console.WriteLine($"{b} % 2 = {b % 2} → {(b % 2 == 0 ? "짝수" : "홀수")}");
Console.WriteLine($"{c} % 2 = {c % 2} → {(c % 2 == 0 ? "짝수" : "홀수")}");
Console.WriteLine($"{d} % 2 = {d % 2} → {(d % 2 == 0 ? "짝수" : "홀수")}");
실행 결과
8 % 2 = 0 → 짝수
13 % 2 = 1 → 홀수
0 % 2 = 0 → 짝수
-7 % 2 = -1 → 홀수
음수는 나머지가 -1이 되므로 % 2 == 1로 홀수를 판정하면 음수에서 틀림. 짝수를 == 0으로 판정하고 나머지를 else로 처리하는 것이 안전함.
using System;
int d = -7;
Console.WriteLine($"% 2 == 1 로 홀수 판정: {d % 2 == 1}"); // 음수에서 틀림
Console.WriteLine($"% 2 != 0 로 홀수 판정: {d % 2 != 0}"); // 음수에서도 맞음
실행 결과
% 2 == 1 로 홀수 판정: False
% 2 != 0 로 홀수 판정: True
핵심은 위에서부터 차례로 검사하고, 처음 참이 된 것 하나만 실행한 뒤 나머지를 건너뛴다는 점임.
using System;
int percent = 45;
if (percent >= 75)
{
Console.WriteLine("상태: 안전");
}
else if (percent >= 50)
{
Console.WriteLine("상태: 보통");
}
else if (percent >= 25)
{
Console.WriteLine("상태: 위험");
}
else
{
Console.WriteLine("상태: 치명");
}
if블록 안에 다시 if 를 넣을 수 있음. 앞 조건이 참인 경우에만 다음 조건을 따져야 할 때 씀.
if 블록 안에 다시 if를 넣을 수 있음. 앞 조건이 참인 경우에만 다음 조건을 따져야 할 때 씀.
using System;
string id = "player1";
string password = "1234";
if (id == "player1")
{
Console.WriteLine("아이디 확인");
if (password == "1234")
{
Console.WriteLine("로그인 성공");
}
else
{
Console.WriteLine("비밀번호가 틀림");
}
}
else
{
Console.WriteLine("없는 아이디");
}
실행 결과
아이디 확인
로그인 성공
바깥 조건이 거짓이면 안쪽은 아예 검사되지 않음. 위 예제에서 아이디가 틀리면 비밀번호는 확인하지 않고 “없는 아이디”만 나옴.
using System;
string id = "guest";
string password = "1234";
if (id == "player1")
{
Console.WriteLine("아이디 확인");
if (password == "1234")
{
Console.WriteLine("로그인 성공");
}
else
{
Console.WriteLine("비밀번호가 틀림");
}
}
else
{
Console.WriteLine("없는 아이디");
}
실행 결과
없는 아이디
갈래마다 다른 처리가 필요하지 않고 모두 참일 때만 실행하면 되는 경우라면, 중첩하지 않고 &&로 묶는 것이 짧고 읽기 쉬움.
using System;
int level = 12;
int stamina = 5;
// 중첩
if (level >= 10)
{
if (stamina > 0)
{
Console.WriteLine("던전에 들어감");
}
}
// 중첩 대신 && 로 묶기
if (level >= 10 && stamina > 0)
{
Console.WriteLine("던전에 들어감");
}
실행 결과
던전에 들어감
던전에 들어감
| 상황 | 형태 |
|---|---|
| 모든 조건이 참일 때만 실행하고, 실패 이유를 구분하지 않음 | &&로 묶음 |
| 어느 조건에서 실패했는지에 따라 다른 처리가 필요함 | 중첩 if |
| 조건이 셋 이상 겹쳐 들여쓰기가 깊어짐 | &&로 묶거나 조건을 bool 변수로 뽑음 |
using System;
int level = 8;
int stamina = 0;
bool hasTicket = false;
// 실패 이유를 알려 줘야 하므로 갈래마다 처리를 둠
if (level < 10)
{
Console.WriteLine("레벨이 낮음");
}
else if (stamina <= 0)
{
Console.WriteLine("행동력이 없음");
}
else if (!hasTicket)
{
Console.WriteLine("입장권이 없음");
}
else
{
Console.WriteLine("던전에 들어감");
}
실행 결과
레벨이 낮음
들어가지 못하는 조건을 먼저 걸러 내고 마지막 else에서 통과 처리를 하는 형태임. 중첩을 깊게 만들지 않으면서 실패 이유를 구분할 수 있음.
if는 조건식이 참인지를 보지만,
switch는 하나의 값이 무엇인지를 보고 갈라냄. 같은 변수를 여러 값과 비교할 때
else if를 늘어놓는 것보다 짧고 의도가 분명함.
switch (검사할 값) //즉 변수
{
case 값1:
// 값1일 때
break;
case 값2:
// 값2일 때
break;
default:
// 어느 case 에도 맞지 않을 때
break;
}
| 부분 | 설명 |
|---|---|
switch (값) | 비교할 값. 변수나 식을 넣음 |
case 값: | 비교 대상. 콜론으로 끝남 |
break; | 이 case 처리를 끝내고 switch를 벗어남 |
default: | 어느 case에도 맞지 않을 때. 생략 가능 |
using System;
int menu = 2;
switch (menu)
{
case 1:
Console.WriteLine("새 게임을 시작함");
break;
case 2:
Console.WriteLine("저장된 게임을 불러옴");
break;
case 3:
Console.WriteLine("게임을 종료함");
break;
default:
Console.WriteLine("없는 메뉴 번호");
break;
}
실행 결과
저장된 게임을 불러옴
case 뒤에 적는 값은 컴파일 시점에 정해지는 상수여야 함. 변수는 쓸 수 없음.
default는 어느 case에도 맞지 않을 때 실행됨.
using System;
int menu = 9;
switch (menu)
{
case 1:
Console.WriteLine("새 게임");
break;
case 2:
Console.WriteLine("이어하기");
break;
default:
Console.WriteLine($"{menu} 번은 없는 메뉴임");
break;
}
실행 결과
9 번은 없는 메뉴임
같은 처리를 해야 하는 값들은 case를 연달아 적어 묶음. 이때는 사이에
break를 넣지 않음.
using System;
int day = 6;
switch (day)
{
case 1:
case 2:
case 3:
case 4:
case 5:
Console.WriteLine("평일");
break;
case 6:
case 7:
Console.WriteLine("주말");
break;
default:
Console.WriteLine("잘못된 요일 번호");
break;
}
실행 결과
주말
case 6:과 case 7:이 같은 블록을 공유함. 실행할 코드가 없는 case를 나열하는 것은 허용되고, 코드가 있는 case에서 break 없이 다음으로 내려가는 것은 허용되지 않음.
switch는 문자열에도 쓸 수 있음. 대소문자는 구분됨.
using System;
string command = "attack";
switch (command)
{
case "attack":
Console.WriteLine("공격함");
break;
case "defend":
Console.WriteLine("방어함");
break;
case "run":
Console.WriteLine("도망침");
break;
default:
Console.WriteLine($"'{command}' 는 알 수 없는 명령임");
break;
}
실행 결과
공격함
using System;
char signal = 'G';
string message;
switch (signal)
{
case 'R':
message = "적색: 멈춤";
break;
case 'Y':
message = "황색: 주의";
break;
case 'G':
message = "녹색: 진행";
break;
default:
message = "신호 없음";
break;
}
Console.WriteLine(message);
실행 결과
녹색: 진행
case에서 변수에 값만 넣고, 출력은 switch 밖에서 한 번만 함.Console.WriteLine을 case마다 반복하지 않아 고칠 곳이 줄어듦.
| 타입 | switch 로 갈라내기 |
|---|---|
int, long, short, byte 등 정수 | 알맞음 |
char | 알맞음 |
string | 알맞음 |
bool | 알맞음 |
float, double, decimal | 문법은 되지만 쓰지 않음 |
switch식에서_는switch문의default에 해당함.
using System;
string grade = "S";
int reward = grade switch
{
"S" => 1000,
"A" => 500,
"B" => 200,
_ => 0
};
Console.WriteLine($"{grade} 등급 보상: {reward}");
실행 결과
S 등급 보상: 1000
switch식은 값을 만들어 내는 식이므로, 어떤 값이 들어와도 결과가 하나 정해져야 함._를 빼면 맞는 것이 없을 때 값을 만들 수 없어 오류가 남.
using System;
int day = 9;
string name = day switch
{
1 => "월요일",
2 => "화요일",
_ => "잘못된 요일 번호"
};
Console.WriteLine(name);
실행 결과
잘못된 요일 번호
_를 빼고 맞지 않는 값을 넣으면 실행 중에 오류가 남.
using System;
int day = 9;
string name = day switch
{
1 => "월요일",
2 => "화요일"
};
Console.WriteLine(name);
실행 결과
Unhandled exception. System.Runtime.CompilerServices.SwitchExpressionException: Non-exhaustive switch expression failed to match its input.
Unmatched value was 9.
마지막 줄 아래로 오류가 난 자리까지의 호출 경로가 함께 찍힘.
컴파일할 때 “모든 경우를 다루지 않았음”이라는 경고도 함께 나옴. switch 식에는 _를 두는 것이 원칙임.
제어문
if와 switchif 문
bool이어야 함. 숫자를 조건으로 쓸 수 없음bool 변수는 == true 없이 그대로 조건으로 씀if (조건);처럼 세미콜론을 붙이면 조건이 무의미해짐else · else if
else는 조건이 거짓일 때 실행됨. 조건을 적지 않음else if는 위에서부터 검사해 처음 참이 된 하나만 실행함else로 잇지 않고 if를 따로 놓음중첩 if
&&로 펴는 것이 읽기 쉬움bool 변수로 뽑거나 실패 조건을 먼저 걸러 냄switch 문
case에 적는 값은 상수여야 하고 변수는 올 수 없음case 구간은 다음 구간으로 흘러내리지 않도록 break 등으로 끝냄. 빈 case 레이블은 연달아 묶을 수 있음case를 연달아 적어 묶음char·string·bool로 갈라내는 데 알맞음. 실수는 문법상 되지만 값이 어긋나기 쉬워 쓰지 않음case에 값을 하나씩 적는 방식으로는 범위를 적을 수 없으므로 범위는 else if로 갈라냄switch 식
값 switch { 대상 => 결과, ... } 형태_가 나머지 전부를 받음. 어떤 값이 와도 결과가 정해져야 함using System;
int hp = 45;
// if · else if · else — 범위로 갈라냄
if (hp <= 0)
{
Console.WriteLine("사망");
}
else if (hp < 30)
{
Console.WriteLine("위험");
}
else
{
Console.WriteLine("정상");
}
// switch 문 — 값으로 갈라내고 여러 문장을 실행함
string command = "attack";
switch (command)
{
case "attack":
Console.WriteLine("공격");
break;
case "defend":
Console.WriteLine("방어");
break;
default:
Console.WriteLine("알 수 없는 명령");
break;
}
// switch 식 — 값을 골라 담음
string grade = "A";
int gold = grade switch
{
"S" => 1000,
"A" => 500,
"B" => 300,
_ => 100
};
Console.WriteLine($"보상 {gold} 골드");
같은 코드를 여러 번 실행하게 만드는 문장
for는 반복에 필요한 세 가지를 괄호 안에 모아 적음.
for (초기식; 조건식; 증감식)
{
// 반복할 코드
}
| 부분 | 언제 실행되는가 | 하는 일 |
|---|---|---|
| 초기식 | 반복 시작 전 한 번만 | 반복 변수를 만들고 시작값을 넣음 |
| 조건식 | 매 반복 직전 | 참이면 본문 실행, 거짓이면 반복 종료 |
| 증감식 | 매 반복 직후 | 반복 변수를 바꿈 |
세 부분은 세미콜론으로 구분함. 마지막 증감식 뒤에는 세미콜론을 붙이지 않음.
조건이 참인 동안
using System;
int count = 0;
while (count < 3)
{
Console.WriteLine("안녕하세요.");
count++;
}
실행 결과
안녕하세요.
안녕하세요.
안녕하세요.
새 글이 올라오면 Develog 알림으로 알려드려요
댓글을 작성하려면 로그인이 필요합니다.
아직 댓글이 없습니다. 첫 번째 댓글을 작성해보세요.
Develog는 단순히 글을 쓰는 공간이 아닙니다. 성장의 과정을 기록하고, 그 기록으로 나를 증명하며 원하는 기회를 얻는 곳이길 바랐습니다. 누군가의 꿈으로 향하는 중간다리가 되는 것, 그것이 Develog를 만든 이유입니다.

게임업계 취업을 준비하다 보면 조금 불편한 현실을 마주하게 됩니다. 게임회사에 들어가고 싶은 사람은 많습니다. 특히 신입 채용은 더 그렇습니다. 공고 하나에 많은 지원자가 몰리고, 회사 입장에서는 비슷한 조건의 지원자 가운데 사람을 선택할 수 있습니다. 그래서 다른 산업에서 흔히 이야기하는 “처음부터 연봉을 낮춰 부르지 마세요.” “적극적으로 협상하세요.”

우리들의 게임 발매 이야기
Develog는 단순히 글을 쓰는 공간이 아닙니다. 성장의 과정을 기록하고, 그 기록으로 나를 증명하며 원하는 기회를 얻는 곳이길 바랐습니다. 누군가의 꿈으로 향하는 중간다리가 되는 것, 그것이 Develog를 만든 이유입니다.


게임업계 취업을 준비하다 보면 조금 불편한 현실을 마주하게 됩니다. 게임회사에 들어가고 싶은 사람은 많습니다. 특히 신입 채용은 더 그렇습니다. 공고 하나에 많은 지원자가 몰리고, 회사 입장에서는 비슷한 조건의 지원자 가운데 사람을 선택할 수 있습니다. 그래서 다른 산업에서 흔히 이야기하는 “처음부터 연봉을 낮춰 부르지 마세요.” “적극적으로 협상하세요.”
