Search

CPP Module 05

Created
2021/10/11
tag
42์„œ์šธ
42Seoul
CPP Module
All of C++98
Exception
try-catch
throw

Subjects

โ€ข

1. ex00 (Mommy, when I grow up, I want to be a bureaucrat!)

Exception & Throw

ex00์€ ๋‹จ ํ•˜๋‚˜์˜ ํด๋ž˜์Šค๋ฅผ ์ •์˜ํ•˜๋ฏ€๋กœ, ๋ฌธ์ œ์—์„œ ์š”๊ตฌํ•˜๋Š” ๊ฒƒ๋“ค์„ Orthodox Canonical Form์„ ๋งž์ถฐ ๊ตฌํ˜„ํ•˜๋ฉด ๋œ๋‹ค. ๋‹ค๋งŒ Exception์ด๋ผ๋Š” ๋‹ค์†Œ ์ƒ์†Œํ•œ ๊ฐœ๋…์„ ์ด์šฉํ•ด์•ผ ํ•˜๋Š”๋ฐ, ์ผ๋ฐ˜์ ์œผ๋กœ ๋ฐœ์ƒํ•˜๋Š” ์—๋Ÿฌ๋“ค์ด Exception์— ์†ํ•œ๋‹ค๊ณ  ๋ณด๋ฉด๋œ๋‹ค. ํŠนํžˆ C++์—์„œ๋Š” <exception>์— std::exception์ด๋ผ๋Š” ํด๋ž˜์Šค๊ฐ€ ์ •์˜๋˜์–ด ์žˆ์œผ๋ฉฐ, ๋ชจ๋“  ์—๋Ÿฌ๋“ค์€ std::exception์„ ๊ธฐ๋ฐ˜ ํด๋ž˜์Šค๋กœ ์ด์šฉํ•˜์—ฌ ๊ตฌํ˜„๋˜์–ด ์žˆ๋‹ค. ๋”ฐ๋ผ์„œ ์ด๋ฅผ ์ƒ์†๋ฐ›์•„ ์‚ฌ์šฉ์ž๊ฐ€ ์›ํ•˜๋Š” ์—๋Ÿฌ๋ฅผ ์ง์ ‘ ์ •์˜ํ•  ์ˆ˜๋„ ์žˆ๊ณ , <stdexcept>์—์„œ ํ•„์š”ํ•œ ์—๋Ÿฌ๋ฅผ ์ง์ ‘ ๊ฐ€์ ธ๋‹ค ์“ธ ์ˆ˜๋„ ์žˆ๋‹ค.
#include <exception> #include <iostream> int main(void) { std::string key; while (true) { std::cin >> key; if (key == "cause") throw (std::exception()); } return (0); }
C++
std::exception ๊ฐ์ฒด๋ฅผ ์ด์šฉํ•  ๋•Œ๋Š” ์œ„ ์ฝ”๋“œ์ฒ˜๋Ÿผ throw ํ‚ค์›Œ๋“œ๋ฅผ ์ด์šฉํ•˜์—ฌ ์—๋Ÿฌ๋ฅผ ๋ฐœ์ƒ์‹œํ‚ฌ ์ˆ˜ ์žˆ๋‹ค. ์—๋Ÿฌ๋ฅผ ๋ฐœ์ƒ์‹œํ‚ค๋Š” ๊ฒƒ์ด ์ข‹๋‹ค ๋‚˜์˜๋‹ค๋ฅผ ๋– ๋‚˜์„œ ์ž‘์„ฑ๋œ ์ฝ”๋“œ๊ฐ€ ์‹คํ–‰๋  ๋•Œ ์›ํ•˜์ง€ ์•Š๋Š” ๋™์ž‘์ด ์ผ์–ด๋‚  ๊ฒฝ์šฐ, ์—๋Ÿฌ๋ฅผ ๋ฐœ์ƒ ์‹œํ‚ค๊ณ  ์ด์— ๋Œ€ํ•ด ์ ์ ˆํ•œ ๋Œ€์ฒ˜๋ฅผ ํ•˜๋Š” ๊ฒƒ์ด ๊ต‰์žฅํžˆ ์ค‘์š”ํ•˜๊ธฐ ๋•Œ๋ฌธ์— std::exception ๊ฐ์ฒด๋ฅผ ์ž˜ ์•Œ์•„๋‘๋Š” ๊ฒƒ์ด ์ข‹๋‹ค.

Custom Exception & what Member Function

class CustomException : public std::exception { public: const char* what(void) const throw() { return ("CustomException"); } };
C++
์ด์ „์— ์ œ์‹œ๋œ ์ฝ”๋“œ์ฒ˜๋Ÿผ std::exception์„ ๊ทธ๋Œ€๋กœ ์ด์šฉํ•  ์ˆ˜๋„ ์žˆ์ง€๋งŒ, ์‚ฌ์šฉ์ž๊ฐ€ ์›ํ•˜๋Š” ์—๋Ÿฌ๋ฅผ ์ •์˜ํ•˜๊ณ  ์‹ถ๋‹ค๋ฉด, ์œ„ ์ฝ”๋“œ์ฒ˜๋Ÿผ std::exception์„ ์ƒ์†ํ•˜์—ฌ ์ง์ ‘ ์—๋Ÿฌ๋ฅผ ์ •์˜ํ•  ์ˆ˜ ์žˆ๋‹ค. ์ฝ”๋“œ๋ฅผ ๋ณด๋ฉด ์ •์˜๋œ ์—๋Ÿฌ์— what์ด๋ผ๋Š” ๋ฉค๋ฒ„ ํ•จ์ˆ˜๋ฅผ ์ •์˜ํ•œ ๊ฒƒ์„ ๋ณผ ์ˆ˜ ์žˆ๋Š”๋ฐ, ์ด๋Š” std::exception์—์„œ ์ •์˜๋œ virtual๋กœ ๋ช…์‹œ๋œ ํ•จ์ˆ˜๋ฅผ Overridingํ•œ ๊ฒƒ์ด๋‹ค. ์ด ๋•Œ what ํ•จ์ˆ˜์˜ ์›ํ˜•์„ ํ†ตํ•ด ๋ช‡ ๊ฐ€์ง€ ์‚ดํŽด๋ณผ ์‚ฌํ•ญ๋“ค์ด ์žˆ๋‹ค.
์ฒซ ์งธ๋กœ const char *๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค๋Š” ์ ์— ์œ ์˜ํ•ด์•ผ ํ•œ๋‹ค. std::string์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ๊ฒƒ์ด ์•„๋‹ˆ๊ธฐ ๋•Œ๋ฌธ์— what ํ•จ์ˆ˜ ๋‚ด๋ถ€์— ์ •์˜ํ•œ std::string์€ ๋ฐ˜ํ™˜๋  ์ˆ˜ ์—†์œผ๋ฉฐ, ํ˜น์—ฌ๋‚˜ std::string์˜ c_str์ด๋ผ๋Š” ๋ฉค๋ฒ„ ํ•จ์ˆ˜๋ฅผ ์ด์šฉํ•˜๋”๋ผ๋„ std::string์ด what ํ•จ์ˆ˜ ๋‚ด๋ถ€์— ์ •์˜๋œ๋‹ค๋ฉด ๋ฐ˜ํ™˜ํ•˜๋ ค๋Š” ๋ฌธ์ž์—ด์˜ ์›๋ณธ ๊ฐ์ฒด๊ฐ€ ์‚ฌ๋ผ์ง€๋ฏ€๋กœ Dangling์— ์ฒ˜ํ•˜๊ฒŒ ๋œ๋‹ค. ๋”ฐ๋ผ์„œ ์ œ์‹œ๋œ ์˜ˆ์‹œ์ฒ˜๋Ÿผ ๋ฆฌํ„ฐ๋Ÿด ๊ฐ’์„ ์ด์šฉํ•˜๊ฑฐ๋‚˜ ์™ธ๋ถ€์—์„œ what์—์„œ๋„ ์ ‘๊ทผํ•  ์ˆ˜ ์žˆ๋Š” ์ ์ ˆํ•œ ๊ฐ’์„ ์ด์šฉํ•˜๋Š” ๊ฒƒ์ด ์ข‹๋‹ค.
๋‘˜ ์งธ๋Š” throw()๋ผ๋Š” ํ‚ค์›Œ๋“œ์ด๋‹ค. ๊ฐ€์žฅ ์œ„์—์„œ ์ œ์‹œ๋œ ์˜ˆ์‹œ์—์„œ std::exception์„ ๋ฐœ์ƒ์‹œํ‚ฌ ๋•Œ throw๋ผ๋Š” ํ‚ค์›Œ๋“œ๋ฅผ ์ด์šฉํ–ˆ๋Š”๋ฐ, ์ด ๋•Œ์˜ throw๋Š” ๋Ÿฐ ํƒ€์ž„์— ์ด์šฉ๋˜๋Š” ํ‚ค์›Œ๋“œ์ด๋‹ค. ๋ฐ˜๋ฉด์— ํ•จ์ˆ˜ ์›ํ˜•์— ์‚ฌ์šฉ๋œ throw๋Š” ์ปดํŒŒ์ผ ํƒ€์ž„์— ์ด์šฉ๋˜๋Š” ํ‚ค์›Œ๋“œ์ด๋ฉฐ, ์ด ๋•Œ๋ฌธ์— throw()๋Š” ๊ณ ์œ ํ•œ ํ•˜๋‚˜์˜ ๊ตฌ๋ฌธ์œผ๋กœ ์ด์šฉ๋œ๋‹ค. ๋”ฐ๋ผ์„œ ํ•จ์ˆ˜ ์›ํ˜•์—์„œ throw()๋ฅผ throw(void)์™€ ํ˜ผ๋™ํ•ด์„  ์•ˆ ๋œ๋‹ค.
ํ•จ์ˆ˜ ์›ํ˜•์— throw(void)๋ฅผ ์ด์šฉํ•˜๋ฉด ์ปดํŒŒ์ผ์ด ๋˜์ง€ ์•Š๋Š”๋‹ค.
ํ•จ์ˆ˜ ์›ํ˜•์— ์‚ฌ์šฉ๋œ throw์— ๋Œ€ํ•ด์„œ ์กฐ๊ธˆ ๋” ์–ธ๊ธ‰ํ•˜์ž๋ฉด, C++17 ์ด์ „์— ์‚ฌ์šฉํ•˜๋Š” Exception Specification์€ 2๊ฐ€์ง€๊ฐ€ ์žˆ๋‹ค. ์ฒซ ์งธ๋Š” Noexcept Specification์ด๋ผ ํ•˜์—ฌ, C++11์—์„œ ์ƒˆ๋กญ๊ฒŒ ์†Œ๊ฐœ๋œ noexcept ํ‚ค์›Œ๋“œ์ด๋‹ค. ์ด๋Š” ํ•จ์ˆ˜๋ฅผ ๋น„์ •์ƒ์ ์œผ๋กœ ํƒˆ์ถœํ•  ์ˆ˜ ์žˆ๋Š” ์ž ์žฌ์ ์ธ Exception์ด ์—†๋‹ค๋Š” ๊ฒƒ์„ ์•Œ๋ฆฌ๋Š”๋ฐ ์ด์šฉ๋œ๋‹ค. ๋‘˜ ์งธ๋Š” Dynamic Exception Specification์ด๋ผ ํ•˜์—ฌ, throw($optional-type-list)๋ฅผ ์ด์šฉํ•˜๋Š” ๊ฒƒ์ด๋‹ค. Dynamic Exception Specification์€ C++11์—์„œ Deprecated๋˜์—ˆ๊ณ , C++17์—์„œ๋Š” throw()๋ฅผ ์ œ์™ธํ•˜๊ณ  ๋ชจ๋‘ ์‚ฌ๋ผ์กŒ๋‹ค. Dynamic Exception Specification์€ ํ•จ์ˆ˜์—์„œ ์–ด๋–ค ์ข…๋ฅ˜์˜ Exception์ด ๋ฐœ์ƒํ•  ์ˆ˜ ์žˆ๋Š”์ง€ ํ•จ์ˆ˜ ์›ํ˜•์—์„œ ๊ฐ„๋‹จํ•˜๊ฒŒ ํŒŒ์•…ํ•  ์ˆ˜ ์žˆ๋„๋ก ์ผ์ข…์˜ ์š”์•ฝ ๊ธฐ๋Šฅ์„ ํ–ˆ์—ˆ๋Š”๋ฐ, ์‹ค์ œ๋กœ ์‚ฌ์šฉํ–ˆ์„ ๋•Œ๋Š” ๋ฌธ์ œ์ ์ด ๋งŽ๋‹ค๋Š” ์ง€์  ๋•Œ๋ฌธ์— ์‚ฌ๋ผ์ง„ ๊ฒƒ์ด๋‹ค. ํ•˜์ง€๋งŒ throw()๋งŒํผ์€ ๋‹ค์†Œ ์œ ์šฉํ•˜๊ฒŒ ์‚ฌ์šฉ๋  ์ˆ˜ ์žˆ๋‹ค๋Š” ๊ฒƒ์ด ์ฆ๋ช…๋˜์–ด throw()๋Š” ๋‚จ์•„ ์žˆ์„ ์ˆ˜ ์žˆ์—ˆ๋‹ค.
์œ„์—์„œ ์„ค๋ช…ํ•œ ๊ฒƒ์ด ๋ง์ด ์กฐ๊ธˆ ์–ด๋ ค์šธ ์ˆ˜ ์žˆ๋Š”๋ฐ Exception Specification์ด๋ผ ํ•˜๋Š” ๊ฒƒ์€ ์—๋Ÿฌ ๋ฐœ์ƒ ์—ฌ๋ถ€๋ฅผ ๋ช…์‹œํ•˜๋Š” ๊ฒƒ์ด๋ผ๊ณ  ์ดํ•ดํ•˜๋ฉด ๋œ๋‹ค. ์ด ๋•Œ ๊ฒฐ๊ณผ์ ์œผ๋กœ ํ™œ์šฉ ๊ฐ€๋Šฅํ•œ ํ‚ค์›Œ๋“œ๋“ค์€ throw()์™€ noexcept๊ฐ€ ๋˜๋Š”๋ฐ, Modern C++์—์„œ๋Š” noexcept๋ฅผ ์ฃผ๋กœ ์ด์šฉํ•œ๋‹ค. ์ฆ‰, throw()์˜ ๊ธฐ๋Šฅ์„ noexcept๊ฐ€ ๋Œ€์ฒดํ•  ์ˆ˜ ์žˆ๋‹ค๋Š” ๊ฒƒ์ธ๋ฐ, ์‹ค์ œ๋กœ throw()๋Š” noexcept(true)์˜ ๋ณ„์นญ์œผ๋กœ ๋™์ž‘ํ•œ๋‹ค. ๊ทธ๋ฆฌ๊ณ  noexcept(true)์—์„œ ์•Œ ์ˆ˜ ์žˆ๋“ฏ์ด, noexcept๋Š” ํ‚ค์›Œ๋“œ ์ž์ฒด๋กœ ์ด์šฉํ•  ์ˆ˜๋„ ์žˆ๊ณ  noexcept($expression) ํ˜•ํƒœ๋กœ ์ด์šฉํ•˜๋Š” ๊ฒƒ๋„ ๊ฐ€๋Šฅํ•˜๋‹ค. $expression ๋ถ€๋ถ„์ด ์ฐธ์ธ์ง€ ๊ฑฐ์ง“์ธ์ง€์— ๋”ฐ๋ผ ์—๋Ÿฌ๊ฐ€ ๋ฐœ์ƒํ•˜๋Š” ํ•จ์ˆ˜์ธ์ง€ ์•„๋‹Œ์ง€๋กœ ์ดํ•ดํ•˜๊ฒŒ ๋œ๋‹ค.
#include <exception> #include <iostream> class CustomException : public std::exception { public: const char* what(void) const throw() { return ("CustomException"); } }; int main(void) { CustomException e; std::cout << e.what() << std::endl; return (0); }
C++
what ํ•จ์ˆ˜ ์›ํ˜•์— ๋Œ€ํ•ด ์ดํ•ดํ–ˆ๊ธฐ ๋•Œ๋ฌธ์—, ์ด๋ฅผ ์ง์ ‘ ํ˜ธ์ถœํ•˜์—ฌ ์–ด๋–ค ์—ญํ• ์„ ํ•˜๋Š”์ง€ ์‚ดํŽด๋ณด์ž. main ํ•จ์ˆ˜์— ์ž‘์„ฑ๋œ ์˜ˆ์‹œ๋Š” ๊ทธ๋ฆฌ ์ข‹์€ ์˜ˆ์‹œ๋Š” ์•„๋‹ˆ์ง€๋งŒ, what ํ•จ์ˆ˜์˜ ์—ญํ• ์„ ์ดํ•ดํ•˜๊ธฐ์—” ์ถฉ๋ถ„ํ•˜๋‹ค. ์‹คํ–‰ ๊ฒฐ๊ณผ๋ฅผ ๋ณด๋ฉด ์•Œ ์ˆ˜ ์žˆ๋“ฏ์ด what ํ•จ์ˆ˜๋Š” ์ •์˜๋œ ์—๋Ÿฌ์— ๋Œ€ํ•œ ๋ฌธ์ž์—ด์„ ๋ฐ˜ํ™˜ํ•œ๋‹ค.

Try ? Catch !

#include <exception> #include <iostream> class CustomException : public std::exception { public: const char* what(void) const throw() { return ("CustomException"); } }; int main(void) { try { std::string key; while (true) { std::cin >> key; if (key == "cause") throw (CustomException()); } } catch (std::exception& e) { std::cerr << e.what() << std::endl; } std::cout << "Program End Normally" << std::endl; return (0); }
C++
Exception์„ ์ •์˜ํ•˜๊ณ  ์ด๋ฅผ throw๋กœ ๋ฐœ์ƒ์‹œํ‚ฌ ์ˆ˜ ์žˆ๋Š” ๊ฒƒ์€ ์•Œ๊ฒŒ ๋˜์—ˆ๋Š”๋ฐ, throw๋œ Exception์€ ๊ฒฐ๊ณผ์ ์œผ๋กœ ํ”„๋กœ๊ทธ๋žจ ์‹คํ–‰ ํ๋ฆ„์„ ๋Š๊ณ  ํ”„๋กœ๊ทธ๋žจ์˜ ์ข…๋ฃŒ๋กœ ์ด์–ด์ง„๋‹ค. ํ•˜์ง€๋งŒ try-catch ๋ฅผ ์ด์šฉํ•˜๋ฉด ๋ฐœ์ƒ๋œ Exception์— ๋Œ€ํ•ด์„œ ํ”„๋กœ๊ทธ๋žจ์˜ ๋น„์ •์ƒ์ ์ธ ์ข…๋ฃŒ๋ฅผ ๋ฐฉ์ง€ํ•˜๊ณ , ๋ฐœ์ƒ๋œ Exception์˜ ํ›„์† ์ž‘์—…์„ ์ •์˜ํ•˜์—ฌ ์ ์ ˆํ•˜๊ฒŒ ์ฒ˜๋ฆฌํ•  ์ˆ˜ ์žˆ๋‹ค. ์ฃผ์–ด์ง„ ์˜ˆ์‹œ๋ฅผ ๋ณด๋ฉด ๊ธฐ์กด์— ์ •์˜ํ•œ CustomException์„ ๋ฐœ์ƒ์‹œ์ผฐ์„ ๋•Œ catch ๊ตฌ๋ฌธ์—์„œ ์žก์„ ์ˆ˜ ์žˆ๋Š” ๊ฒƒ์„ ๋ณผ ์ˆ˜ ์žˆ๋‹ค. ์ด ๋•Œ, Exception์ด ๋ฐœ์ƒํ•  ์ˆ˜ ์žˆ๋Š” ๊ตฌ๋ฌธ๋“ค์ด try ๊ตฌ๋ฌธ์˜ ๋ฒ”์œ„์— ์†ํ•ด์žˆ์ง€ ์•Š์œผ๋ฉด try-catch ์Œ์œผ๋กœ ๋ถ™์€ catch์—์„œ๋Š” Exception์„ ์žก์„ ์ˆ˜ ์—†๋‹ค. ์ฆ‰, catch์—์„œ ์žก๊ณ  ์‹ถ์€ Exception์€ ๋ฐ˜๋“œ์‹œ ์Œ์œผ๋กœ ๋ถ™์€ try ๋‚ด์—์„œ ์‹œ๋„๋˜์–ด์•ผ ํ•œ๋‹ค.
#include <exception> #include <iostream> class CustomException : public std::exception { public: const char* what(void) const throw() { return ("CustomException"); } }; int main(void) { while (true) { try { std::string key; while (true) { std::cin >> key; if (key == "cause") throw (CustomException()); if (key == "int") throw (1); if (key == "double") throw (0.5); } } catch (std::exception& e) { std::cerr << e.what() << std::endl; } catch (int& i) { std::cerr << "Int Caught" << std::endl; } catch (double& d) { std::cerr << "Double Caught" << std::endl; } std::cout << "Program End Normally" << std::endl; } return (0); }
C++
๊ทธ๋ฆฌ๊ณ  catch๋ฅผ ์ด์šฉํ•˜์—ฌ Exception์„ ์žก์„ ๋•Œ std::exception& e ๋ผ๋Š” ๊ตฌ๋ฌธ์ด ์ด์šฉ๋œ ๊ฒƒ์„ ๋ณผ ์ˆ˜ ์žˆ๋Š”๋ฐ, ์ผ๋ฐ˜์ ์œผ๋กœ Exception๋“ค์€ std::exception์„ ๊ธฐ๋ฐ˜ ํด๋ž˜์Šค๋กœ ์ด์šฉํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์–ด์ง€๊ฐ„ํ•œ Exception๋“ค์€ std::exception& e ๊ตฌ๋ฌธ์œผ๋กœ ๋ชจ๋‘ ์žก์•„๋‚ผ ์ˆ˜ ์žˆ๋‹ค. ํ•˜์ง€๋งŒ throw๋ฅผ Exception์— ๋Œ€ํ•ด์„œ๋งŒ ์ˆ˜ํ–‰ํ•  ์ˆ˜ ์žˆ๋Š” ๊ฒƒ์€ ์•„๋‹ˆ๋‹ค. ์œ„ ์˜ˆ์‹œ๋ฅผ ๋ณด๋ฉด ๊ฒฝ์šฐ์— ๋”ฐ๋ผ์„œ int ํ˜น์€ double ๋“ฑ์ด throw๋˜๋Š” ๊ฒƒ์„ ๋ณผ ์ˆ˜ ์žˆ๋Š”๋ฐ, ์ด๋Š” ๋‹ค์ค‘์œผ๋กœ ์ž‘์„ฑ๋œ catch๋ฅผ ์ด์šฉํ•˜์—ฌ ์žก์•„๋‚ผ ์ˆ˜ ์žˆ๋‹ค.
#include <exception> #include <iostream> class CustomException : public std::exception { public: const char* what(void) const throw() { return ("CustomException"); } }; int main(void) { while (true) { try { std::string key; while (true) { std::cin >> key; if (key == "cause") throw (CustomException()); if (key == "int") throw (1); if (key == "double") throw (0.5); } } catch (std::exception& e) { std::cerr << e.what() << std::endl; } catch (...) { std::cerr << "Numeric Caught" << std::endl; } std::cout << "Program End Normally" << std::endl; } return (0); }
C++
๊ทธ๋ ‡๋‹ค๋ฉด Exception์— ๋Œ€ํ•ด์„œ ๋ชจ๋“  catch ๊ตฌ๋ฌธ์„ ์ž‘์„ฑํ•˜์ง€ ์•Š๊ณ , ์ƒํ™ฉ์— ๋”ฐ๋ผ int, double ๋“ฑ์„ ํ•œ ๋ฒˆ์— ๋ฌถ์–ด์„œ ์ฒ˜๋ฆฌํ•˜๊ณ  ์‹ถ์€ ๊ฒฝ์šฐ์—๋Š” ์–ด๋–ป๊ฒŒ ํ•ด์•ผํ• ๊นŒ? ๊ทธ ๋‹ต์€ ์˜ˆ์‹œ๋ฅผ ๋ณด๋ฉด ์•Œ ์ˆ˜ ์žˆ๋‹ค. catch์— ... ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋‚˜๋จธ์ง€ ๊ฒฝ์šฐ๋“ค์„ ๋ชจ๋‘ ์ฒ˜๋ฆฌํ•  ์ˆ˜ ์žˆ๋‹ค. ๋‹จ, ํ”„๋กœ๊ทธ๋žจ์ด Exception์— ๋Œ€ํ•ด์„œ ์ ์ ˆํ•œ ์ฒ˜๋ฆฌ๋ฅผ ํ•  ์ˆ˜ ์žˆ๋„๋ก ์ž‘์„ฑ๋œ ๊ฒƒ์ด ์•„๋‹ˆ๋ผ๋ฉด, ... ์„ ๋ฌด๋ถ„๋ณ„ํ•˜๊ฒŒ ์‚ฌ์šฉํ•˜๋Š” ํ–‰์œ„์— ์ฃผ์˜ํ•ด์•ผ ํ•œ๋‹ค.
์ผ๋ฐ˜์ ์œผ๋กœ catch์˜ ... ์—์„œ๋Š” Exception ๋ฐœ์ƒ์„ ๊ธฐ๋กํ•˜๋Š” ์ž‘์—… ๋“ฑ์„ ์ˆ˜ํ–‰ํ•œ๋‹ค.

Stack Unwinding

๊ธฐ๋ณธ์ ์œผ๋กœ Exception์ด throw๋˜๋ฉด, throw ๊ตฌ๋ฌธ ์ดํ›„๋กœ๋Š” ์ฝ”๋“œ๊ฐ€ ์‹คํ–‰๋˜์ง€ ์•Š๋Š”๋‹ค. ๋”ฐ๋ผ์„œ ์ œ์‹œ๋œ ์˜ˆ์‹œ๋“ค์„ ์ ์ ˆํžˆ ์ˆ˜์ •ํ•ด์„œ throw ์ดํ›„์˜ ์ถœ๋ ฅ๋ฌธ๋“ค์„ ์ž‘์„ฑํ•ด๋ณด๋ฉด, ํ•ด๋‹น ์ถœ๋ ฅ๋ฌธ๋“ค์€ ์ œ ๊ธฐ๋Šฅ์„ ํ•˜์ง€ ์•Š๊ณ  catch๋กœ ๋น ์ง€๋Š” ๊ฒƒ์„ ๋ณผ ์ˆ˜ ์žˆ๋‹ค. ๊ทธ๋ ‡๋‹ค๋ฉด ๋งŒ์ผ ํŠน์ • ํ•จ์ˆ˜์—์„œ ๊ฐ์ฒด๋ฅผ ์ด์šฉํ•˜๊ณ  ์žˆ์—ˆ๊ณ , throw๋กœ Exception์„ ๋˜์กŒ๋‹ค๋ฉด ๊ฐ์ฒด๋Š” ์ ์ ˆํžˆ ์†Œ๋ฉธ๋  ์ˆ˜ ์žˆ์„๊นŒ?
๋งŒ์ผ ๊ฐ์ฒด๋“ค์ด ์˜คํ† ๋งคํ‹ฑ์œผ๋กœ ์„ ์–ธ๋˜์—ˆ๋‹ค๋ฉด, throw๋กœ ๋˜์ ธ์ง„ Exception์ด catch ๊ตฌ๋ฌธ์ด ์กด์žฌํ•˜๋Š” ์Šคํƒ ํ”„๋ ˆ์ž„์— ๋„๋‹ฌํ•˜๊ธฐ ์ „๊นŒ์ง€ ์ ์ ˆํ•˜๊ฒŒ ์ž์‹ ์˜ ์†Œ๋ฉธ์ž๋ฅผ ํ˜ธ์ถœํ•˜๊ฒŒ ๋œ๋‹ค. ์ด๋ฅผ Stack Unwinding์ด๋ผ ํ•œ๋‹ค. ํ•ด๋‹น ๊ธฐ๋Šฅ์€ ํ•จ์ˆ˜ ํ˜ธ์ถœ์„ ๋งˆ์น˜๊ณ  ์Šคํƒ ํ”„๋ ˆ์ž„์„ ๊ฑท์–ด๋‚ด๋ฉด์„œ ์˜คํ† ๋งคํ‹ฑ๋“ค์ด ์†Œ๋ฉธ๋˜๋Š” ๊ฒƒ๊ณผ ๋™์ผํ•˜๊ฒŒ ๋™์ž‘ํ•˜๋Š”๋ฐ, ์ด๋Š” Exception์ด ๋ฐœ์ƒํ–ˆ์„ ๋•Œ๋„ ์˜คํ† ๋งคํ‹ฑ๋“ค์ด ์ •์ƒ์ ์œผ๋กœ ์†Œ๋ฉธํ•˜๋Š” ๊ฒƒ์„ ๋ณด์žฅํ•˜๋Š” ์—ญํ• ์„ ํ•œ๋‹ค.
๋‹ค๋งŒ ์ฃผ์˜ํ•ด์•ผ ํ•  ์ ์€ Stack Unwinding์€ ์˜คํ† ๋งคํ‹ฑ์— ๋Œ€ํ•ด์„œ๋งŒ ๋™์ž‘ํ•˜๊ธฐ ๋•Œ๋ฌธ์—, ์ž์œ  ๊ณต๊ฐ„์— ํ• ๋‹น๋œ ๊ฐ์ฒด๋Š” ํ•ด๋‹น๋˜์ง€ ์•Š๋Š”๋‹ค๋Š” ๊ฒƒ์ด๋‹ค. ๋งŒ์ผ ์›์‹œ ํฌ์ธํ„ฐ์— new๋กœ ์ƒ์„ฑํ•œ ๊ฐ์ฒด๋ฅผ ํ• ๋‹นํ–ˆ๋‹ค๋ฉด, ์ด๋Š” ๋ฉ”๋ชจ๋ฆฌ ๋ˆ„์ˆ˜๋กœ ์ด์–ด์งˆ ์ˆ˜ ์žˆ๋‹ค. Exception ๋ฐœ์ƒ ์ง€์ ๊ณผ catch์˜ ์‹œ์ ์ด ๋™์ผํ•œ ์Šคํƒ ํ”„๋ ˆ์ž„ ๋‚ด์—์„œ ์ด๋ค„์ง„๋‹ค๋ฉด catch ๊ตฌ๋ฌธ์—์„œ ์–ด์ฐŒ์ €์ฐŒ ๋ฉ”๋ชจ๋ฆฌ๋ฅผ ํ•ด์ œํ•  ์ˆ˜๋Š” ์žˆ์ง€๋งŒ, catch์˜ ์‹œ์ ์ด ๋™์ผํ•˜์ง€ ์•Š๋‹ค๋ฉด ๋™์ผํ•œ ์‹œ์ ์— catch๋ฅผ ํ•œ ๋ฒˆ ๋” ์ž‘์„ฑํ•˜๊ณ  ๋‹ค์‹œ throw๋ฅผ ๋˜์ง€๋Š” ๋ถˆํ•„์š”ํ•œ ์ž‘์—…์ด ์ƒ๊ธด๋‹ค. ๋”ฐ๋ผ์„œ ์ž์œ  ๊ณต๊ฐ„์— ํ• ๋‹น๋œ ๊ฐ์ฒด๋Š” Stack Unwinding ์‹œ์— ์†Œ๋ฉธ์ž๋ฅผ ํ˜ธ์ถœํ•˜์ง€ ์•Š๋Š”๋‹ค๋Š” ์ ์„ ๋ช…์‹ฌํ•˜์—ฌ ์ฝ”๋“œ๋ฅผ ์ž‘์„ฑํ•ด์•ผ ํ•œ๋‹ค.
์›์‹œ ํฌ์ธํ„ฐ์˜ ์•ฝ์ ์ด ์ง€๋‚œ Module 04 ๊ธ€์—์„œ๋„ ์–ธ๊ธ‰๋˜์—ˆ๋Š”๋ฐ, Stack Unwinding ์‹œ์— ๋ฐœ์ƒํ•  ์ˆ˜ ์žˆ๋Š” ๋ฌธ์ œ ์—ญ์‹œ ์Šค๋งˆํŠธ ํฌ์ธํ„ฐ๋กœ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ๋‹ค. ์Šค๋งˆํŠธ ํฌ์ธํ„ฐ๋Š” ๊ฐ์ฒด์ด๋ฏ€๋กœ Stack Unwinding ์‹œ์— ์†Œ๋ฉธ์ž๋ฅผ ํ˜ธ์ถœํ•  ์ˆ˜ ์žˆ๊ณ , ์†Œ๋ฉธ์ž ๋‚ด์—์„œ ์ฐธ์กฐ ๋Œ€์ƒ์˜ ๋ฉ”๋ชจ๋ฆฌ ๋ฐ˜ํ™˜์„ ์œ ๋„ํ•  ์ˆ˜ ์žˆ๋‹ค.
Exception์ด ๋ฌด์—‡์ธ์ง€, throw์™€ try-catch์ด ๋ฌด์—‡์ธ์ง€ ์ดํ•ดํ–ˆ๊ธฐ ๋•Œ๋ฌธ์— ์ถฉ๋ถ„ํ•œ Error Handling์ด ๊ฐ€๋Šฅํ•˜๋‹ค. ๋‚จ์€ ex01 - ex03๊นŒ์ง€ ์ ์ ˆํ•˜๊ฒŒ Error Handling์„ ํ•˜๋ฉด์„œ ์ฝ”๋“œ๋ฅผ ์ž‘์„ฑํ•˜๋ฉด ๋˜๋Š”๋ฐ, ๋งค๋ฒˆ์˜ ์ž‘์—…๋งˆ๋‹ค throw๋ฅผ ๋˜์ง€๊ฒŒ ๋งŒ๋“ค์–ด์„œ ๋ฐ˜๋ณต๋œ try-catch๋ฅผ ์ž‘์„ฑํ•˜๋Š” ๊ฒƒ์„ ์ตœ๋Œ€ํ•œ ์ง€์–‘ํ•˜์ž. Error Handling์ด ๊ท€์ฐฎ์€ ์ž‘์—…์œผ๋กœ ๋‚จ๊ฒŒ ๋งŒ๋“ค์ง€ ๋ง๊ณ , ํ”„๋กœ๊ทธ๋ž˜๋ฐ์„ ํ•˜๋Š” ์ž…์žฅ์—์„œ ๋” ํŽธ๋ฆฌํ•œ ์ˆ˜๋‹จ์ด ๋  ์ˆ˜ ์žˆ๋„๋ก ์ ์ ˆํ•œ ๊ตฌ์กฐ๋ฅผ ์ƒ๊ฐํ•˜๋Š” ์Šต๊ด€์„ ๋งŒ๋“ค์ž.

Bureaucrat Exception

๋ฌธ์ œ์—์„œ ์ œ์‹œํ•œ Bureaucrat ํด๋ž˜์Šค์—์„œ๋Š” GradeTooHighException๊ณผ GradeTooLowException์„ ์ž‘์„ฑํ•˜๋ฉด ๋œ๋‹ค๊ณ  ํ–ˆ์œผ๋ฏ€๋กœ, ์œ„์—์„œ ์ดํ•ดํ•œ ๊ฒƒ์„ ํ† ๋Œ€๋กœ ์ž‘์„ฑํ•ด์ฃผ๋ฉด ๋œ๋‹ค. ๊ทธ๋ฆฌ๊ณ  incrementGrade ํ•จ์ˆ˜์™€ decrementGrade ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœ ํ–ˆ์„ ๋•Œ, ๋ฌธ์ œ๊ฐ€ ๋˜๋Š” ์ƒํ™ฉ์—์„œ ๊ธฐ์กด์— ์ •์˜ํ•œ Exception๋“ค์„ ์ ์ ˆํžˆ ๋ฐœ์ƒ์‹œ์ผœ์ฃผ๋ฉด ๋œ๋‹ค. ๋‹ค๋งŒ, Increment์™€ Decrement์˜ ๋ฐฉํ–ฅ์— ๋Œ€ํ•ด์„œ ์ฃผ์˜ํ•˜์ž.

2. ex01 (Form up, maggots!)

Make Exception

ex00์˜ Bureaucrat ํด๋ž˜์Šค์ฒ˜๋Ÿผ, Form ํด๋ž˜์Šค ์—ญ์‹œ ์ ์ ˆํ•œ Grade๋ฅผ ๊ฐ–๊ณ  ์žˆ์ง€ ์•Š์œผ๋ฉด Exception์„ ๋˜์ง€๋„๋ก ๋งŒ๋“ค์–ด์•ผ ํ•œ๋‹ค. ์ด์™€ ๊ฐ™์€ ์ž‘์—…์€ Form ํด๋ž˜์Šค ์ƒ์„ฑ ๋‹จ๊ณ„์˜ ์ƒ์„ฑ์ž์—์„œ ์ฒ˜๋ฆฌํ•˜๋ฉด ๋œ๋‹ค.

Const Variable

Form ํด๋ž˜์Šค์˜ ๋ฉค๋ฒ„ ๋ณ€์ˆ˜๋“ค์€ ๋Œ€์ฒด์ ์œผ๋กœ const๋กœ ์ •์˜๋˜์–ด ์žˆ๋Š”๋ฐ, ์ด ๋•Œ๋ฌธ์— operator=์—์„œ ์–ด๋ ค์›€์„ ๊ฒช์„ ์ˆ˜ ์žˆ๋‹ค. ํ•ด๋‹น ๋ณ€์ˆ˜๋“ค์€ Module 02์—์„œ ๋ฐฐ์› ๋˜ ๊ฒƒ์ฒ˜๋Ÿผ const_cast<T>๋ฅผ ์ด์šฉํ•˜์—ฌ const ๊ฐ’์„ ๋ฐ”๊พธ๋Š” ๊ฒƒ์ด ๊ฐ€๋Šฅํ•˜๋‹ค.

Less Code

Form ํด๋ž˜์Šค์˜ beSigned ํ•จ์ˆ˜์™€ Bureaucrat ํด๋ž˜์Šค์˜ signForm ํ•จ์ˆ˜๊ฐ€ ์žˆ๋Š”๋ฐ, ์ด๋“ค์„ main ํ•จ์ˆ˜์—์„œ ์ผ์ผ์ด ํ˜ธ์ถœํ•˜๋Š” ์ž‘์—…์„ ๊ฑฐ์น˜๊ฒŒ ๋˜๋ฉด try-catch ๊ตฌ๋ฌธ ์—ญ์‹œ ์ผ์ผ์ด ๋‚˜์—ดํ•˜์—ฌ ์ž‘์„ฑํ•ด์•ผ ํ•œ๋‹ค. ์„œ๋ธŒ์ ํŠธ์—์„œ๋Š” beSigned ํ•จ์ˆ˜์—์„œ ์„œ๋ช…์„ ํ•  ์ˆ˜ ์—†์„ ๋•Œ Exception์„ ๋˜์ง€๋Š” ๊ฒƒ์œผ๋กœ ๊ธฐ๋Šฅ์„ ์ •ํ•ด๋‘์—ˆ๊ณ , signForm์—์„œ๋Š” ์„œ๋ช… ์ˆ˜ํ–‰ ์—ฌ๋ถ€๋ฅผ ์ถœ๋ ฅํ•˜๋ผ๊ณ  ๋‚˜์™€ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ๋‘ ํ•จ์ˆ˜๋ฅผ ์—ฎ์„ ์ˆ˜ ์žˆ์Œ์„ ์•Œ ์ˆ˜ ์žˆ๋‹ค. ๋”ฐ๋ผ์„œ ์ธ์ž๋กœ ๋ฐ›์€ Form ํด๋ž˜์Šค์˜ ๊ฐ์ฒด๋ฅผ ์ด์šฉํ•˜์—ฌ signForm ํ•จ์ˆ˜ ๋‚ด์—์„œ beSigned ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•˜๋„๋ก ๋งŒ๋“ค๊ณ , ์ด์™€ ๊ฐ™์€ ๊ณผ์ •์„ signForm ํ•จ์ˆ˜ ๋‚ด์—์„œ try-catch๋กœ ๋ฌถ์–ด์„œ ๊ฒฐ๊ณผ๊นŒ์ง€ ์ถœ๋ ฅํ•˜๋„๋ก ๋งŒ๋“ค๋ฉด main ํ•จ์ˆ˜์—์„œ ๋งŽ์€ ์ฝ”๋“œ๋“ค์„ ์•„๋‚„ ์ˆ˜ ์žˆ๋‹ค.

3. ex02 (No, you need form 28B, not 28C...)

Turn into Abstract Class

ex01์—์„œ Form ํด๋ž˜์Šค๋งŒ ๊ผผ๊ผผํžˆ ์ž‘์„ฑํ–ˆ๋‹ค๋ฉด, ex02์—์„œ๋Š” ํฌ๊ฒŒ ํ•ด์ค„ ๊ฒƒ์ด ์—†๋‹ค. ์ƒˆ๋กญ๊ฒŒ ์ƒ๊ธฐ๋Š” PresidentialPardonForm ํด๋ž˜์Šค (์ดํ•˜ P ํด๋ž˜์Šค), RobotomyRequestForm (์ดํ•˜ R ํด๋ž˜์Šค), ShrubberyCreationForm (์ดํ•˜ S ํด๋ž˜์Šค)๋ฅผ ์ •์˜ํ•ด์•ผ ํ•˜๊ณ , Form ํด๋ž˜์Šค์˜ execute๋ฅผ ๊ฐ ํด๋ž˜์Šค์— ๋งž๊ฒŒ Overriding ํ•˜๋ฉด ๋œ๋‹ค. ๋˜ํ•œ Form ํด๋ž˜์Šค๋ฅผ ์ถ”์ƒ ํด๋ž˜์Šค๋กœ ๋งŒ๋“ค์–ด์•ผ ๋˜๋ฏ€๋กœ, execute ํ•จ์ˆ˜๋ฅผ Pure Virtual Function์œผ๋กœ ์„ ์–ธํ•˜์—ฌ ํ•ด๊ฒฐํ–ˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์žŠ์ง€ ์•Š๊ณ  ์†Œ๋ฉธ์ž์— virtual์„ ๋ช…์‹œํ•˜์ž.
๋ฉค๋ฒ„ ๋ณ€์ˆ˜๋“ค์€ ๋ฌธ์ œ ์กฐ๊ฑด์— ๋”ฐ๋ผ protected๋กœ ๋ฐ”๊ฟ”์„  ์•ˆ ๋œ๋‹ค.

More Reusable

Form ํด๋ž˜์Šค๋“ค์˜ execute ํ•จ์ˆ˜ ์ถ”๊ฐ€์— ๋”ฐ๋ผ, Bureaucrat ํด๋ž˜์Šค์—์„œ๋„ executeForm ํ•จ์ˆ˜๋ฅผ ์ถ”๊ฐ€ํ•ด์•ผ ํ•œ๋‹ค. ๋‹จ, ๋‚ด ๊ฒฝ์šฐ์—๋Š” ex01์˜ signForm๊ณผ ๋งˆ์ฐฌ๊ฐ€์ง€๋กœ executeForm๊ณผ execute๋ฅผ ๋”ฐ๋กœ ํ˜ธ์ถœํ•˜์ง€ ์•Š๋„๋ก, ์ธ์ž๋กœ ๋ฐ›์€ Form ํด๋ž˜์Šค์˜ ๊ฐ์ฒด๋กœ execute ํ•จ์ˆ˜๋ฅผ executeForm ํ•จ์ˆ˜ ๋‚ด์—์„œ ํ˜ธ์ถœํ•˜๋Š” ์‹์œผ๋กœ ์ž‘์„ฑํ–ˆ๋‹ค. ์ด ๋•Œ์˜ try-catch๋Š” executeForm์— ๊ฑธ์–ด๋‘์—ˆ๊ณ , execute ํ•จ์ˆ˜์—์„œ ๋ฐœ์ƒํ•œ Exception๊นŒ์ง€ ์žก์•„์„œ ๊ฒฐ๊ณผ๋ฅผ ์ถœ๋ ฅํ•˜๊ฒŒ ๋งŒ๋“ค์–ด main ํ•จ์ˆ˜์—์„œ ์ž‘์„ฑํ•  try-catch๋ฅผ ์•„๋ผ๋Š” ๋ฐฉํ–ฅ์œผ๋กœ ๊ตฌํ˜„ํ–ˆ๋‹ค.
ํŠนํžˆ execute ํ•จ์ˆ˜ ๋‚ด์—์„œ๋Š” ์‹คํ–‰ ์—ฌ๋ถ€ ๋“ฑ์„ ํŒŒ์•…ํ•˜์—ฌ ์‹คํ–‰์ด ๋ถˆ๊ฐ€๋Šฅํ•  ๋•Œ๋Š” Exception์„ ๋˜์ง€๋„๋ก ๋งŒ๋“ค์–ด์•ผ ํ•˜๋Š”๋ฐ, ์‹คํ–‰ ์—ฌ๋ถ€์˜ ํŒŒ์•…์ด 3๊ฐœ์˜ ํด๋ž˜์Šค์—์„œ ๋ชจ๋‘ ์ค‘๋ณต๋œ๋‹ค. ๋”ฐ๋ผ์„œ ์ด ๋ถ€๋ถ„๋„ Form ํด๋ž˜์Šค์— ๋ฏธ๋ฆฌ ์ •์˜ํ•ด๋‘๋ฉด, 3๊ฐœ์˜ ํŒŒ์ƒ ํด๋ž˜์Šค์—์„œ๋„ ์ด๋ฅผ ์žฌ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ execute ํ•จ์ˆ˜์—์„œ๋Š” ๋‹จ์ˆœํžˆ ์‹คํ–‰ ์—ฌ๋ถ€ ํŒŒ์•…์„ ์œ„ํ•œ ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•˜๊ธฐ๋งŒ ํ•˜๋ฉด ๋œ๋‹ค. ๋ฌธ์ œ๊ฐ€ ์—†๋‹ค๋ฉด ๋‹ค์Œ ์ฝ”๋“œ๋กœ ๋„˜์–ด๊ฐˆ ๊ฒƒ์ด๊ณ , ๋ฌธ์ œ๊ฐ€ ์žˆ๋‹ค๋ฉด Exception์— ์˜ํ•ด execute ํ•จ์ˆ˜์˜ ๋‚˜๋จธ์ง€ ๋ถ€๋ถ„์€ ์‹คํ–‰๋˜์ง€ ์•Š์„ ๊ฒƒ์ด๋‹ค.
์ „์ฒด์ ์œผ๋กœ ์„œ๋ช…์ด ๋˜์ง€ ์•Š์•˜์„ ๋•Œ์˜ Exception๊ณผ ํŠนํžˆ S ํด๋ž˜์Šค์—์„œ๋Š” std::ofstream์— ๋Œ€ํ•œ Exception๋„ ์ถ”๊ฐ€๋˜๋ฉด ์ข‹์„ ๊ฒƒ์ด๋‹ค.
๊ทธ๋ฆฌ๊ณ  ์„œ๋ธŒ์ ํŠธ์—์„œ ์ฃผ์–ด์ง„ target์„ ์–ด๋–ป๊ฒŒ ํ•ด์„ํ•˜๋Š”์ง€์— ๋”ฐ๋ผ ๋‹ค๋ฅด๊ฒ ์ง€๋งŒ, ๋‚˜๋Š” target์„ name์œผ๋กœ ์ƒ๊ฐํ•˜์—ฌ ์ƒˆ๋กญ๊ฒŒ ์ •์˜ํ•œ 3๊ฐœ์˜ ํด๋ž˜์Šค์— ์ถ”๊ฐ€์ ์ธ ๋ฉค๋ฒ„ ๋ณ€์ˆ˜๋ฅผ ๋‘์ง€ ์•Š๊ณ  ๊ธฐ์กด์˜ Form ํด๋ž˜์Šค๋ฅผ ๊ทธ๋Œ€๋กœ ์ด์šฉํ•˜๊ฒŒ ๋‘์—ˆ๋‹ค. ์ด ๋•Œ ๊ฐ ํด๋ž˜์Šค๊ฐ€ ์ž์‹ ์˜ ํƒ€์ž…์„ ์•Œ ์ˆ˜ ์žˆ๋„๋ก Form ํด๋ž˜์Šค์— type์„ ์ •์˜ํ–ˆ๊ณ , ๊ฐ ํด๋ž˜์Šค์— ๋งž๋Š” ํƒ€์ž…์„ ์ด์šฉํ•˜๋„๋ก ์ƒ์„ฑ์ž์—์„œ ๊ทธ ๊ฐ’์„ ๊ฐฑ์‹ ํ•˜๋„๋ก ์ž‘์„ฑํ–ˆ๋‹ค. ๋•๋ถ„์— ์ƒˆ๋กญ๊ฒŒ ์ •์˜ํ•œ 3๊ฐœ์˜ ํด๋ž˜์Šค์—๋Š” execute ํ•จ์ˆ˜๋ฅผ ์ œ์™ธํ•˜๋ฉด, ์ด๋ฆ„ ์žˆ๋Š” ์ƒ์„ฑ์ž์™€ Orthodox Canonical Form ๋ฐ–์— ์—†๊ธฐ ๋•Œ๋ฌธ์— ๋Œ€๋ถ€๋ถ„์˜ ์—ฐ์‚ฐ์„ Form ํด๋ž˜์Šค์˜ ์—ฐ์‚ฐ์œผ๋กœ ๋Œ€์ฒดํ•  ์ˆ˜ ์žˆ์—ˆ๋‹ค.
๊ฐ ํด๋ž˜์Šค์˜ ํƒ€์ž…์„ ๊ฐฑ์‹ ํ•  ๋•Œ ํด๋ž˜์Šค๋งˆ๋‹ค ์‚ฌ์šฉํ•˜๋Š” ๊ฐ’์ด ๋‹ค๋ฅธ๋ฐ, ์ฝ”๋“œ์˜ ์ ์‘์„ฑ์„ ๋†’์ด๊ธฐ ์œ„ํ•ด #define์œผ๋กœ ๊ฐ ํƒ€์ž…์„ ์ •์˜ํ•ด๋‘์—ˆ๋‹ค.
PresidentialPardonForm& PresidentialPardonForm::operator=(const PresidentialPardonForm& p) { return (*(dynamic_cast<PresidentialPardonForm*>(&(Form::operator=(p))))); }
C++
P ํด๋ž˜์Šค๋ฅผ ์˜ˆ๋กœ ๋“ค์ž๋ฉด, ํŒŒ์ƒ ํด๋ž˜์Šค์˜ ํ• ๋‹น ์—ฐ์‚ฐ์€ Form::operator=๋ฅผ ํ˜ธ์ถœํ•˜๋„๋ก ๋‘์—ˆ๋‹ค. ์ด ๋•Œ์˜ ๋ฐ˜ํ™˜ ๊ฐ’์€ ํ•ด๋‹น ๋ฉค๋ฒ„ ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•œ P ํด๋ž˜์Šค์˜ ๊ฐ์ฒด๊ฐ€ ๋˜๋Š”๋ฐ, Form::operator=์˜ ๋ฐ˜ํ™˜์€ Form ํด๋ž˜์Šค์˜ ๊ฐ์ฒด์ด๋ฏ€๋กœ P ํด๋ž˜์Šค์˜ ์ฐธ์กฐ์ž๋กœ ๋‹ค์šด ์บ์ŠคํŒ…์ด ๋˜์–ด ๋Ÿฐ ํƒ€์ž„์— ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•˜๊ฒŒ ๋œ๋‹ค. ์ด๋Š” ์ปดํŒŒ์ผ ํƒ€์ž„์— ๋ฐœ์ƒํ•˜๋Š” ์—๋Ÿฌ๊ฐ€ ์•„๋‹ˆ๋ฏ€๋กœ ๊ฝค๋‚˜ ์น˜๋ช…์ ์ด๋‹ค. ๋”ฐ๋ผ์„œ ํ•ด๋‹น ๊ฒฝ์šฐ์—๋Š” P ํด๋ž˜์Šค โ†’ Form ํด๋ž˜์Šค โ†’ P ํด๋ž˜์Šค์˜ ํ˜• ๋ณ€ํ™˜์ด ์ด๋ค„์ง€๋Š” ๊ฒƒ์„ ํ†ตํ•ด Form ํด๋ž˜์Šค์˜ ๋ฐ˜ํ™˜์ด P ํด๋ž˜์Šค ์ž„์„ ๋ณด์žฅํ•  ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ, ์œ„ ์ฝ”๋“œ์ฒ˜๋Ÿผ dynamic_cast<T>๋ฅผ ์ด์šฉํ•˜์—ฌ ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ๋‹ค.
๋ฉ”๋ชจ๋ฆฌ ๋ ˆ์ด์•„์›ƒ์—์„œ ํŒŒ์ƒ ํด๋ž˜์Šค๋Š” ๊ธฐ๋ฐ˜ ํด๋ž˜์Šค๋ฅผ ๊ฐ–๊ณ  ์žˆ์–ด์„œ ์—… ์บ์ŠคํŒ…์ด ๊ฐ€๋Šฅํ•˜์ง€๋งŒ, ๊ธฐ๋ฐ˜ ํด๋ž˜์Šค๋Š” ํŒŒ์ƒ ํด๋ž˜์Šค๋ฅผ ๊ฐ–๊ณ  ์žˆ์ง€ ์•Š์„ ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ ๋‹ค์šด ์บ์ŠคํŒ…์— ์—„๊ฒฉํ•˜๋‹ค.
PresidentialPardonForm::PresidentialPardonForm(const PresidentialPardonForm& p) : Form(p) { setType(P_NAME); }
C++
operator= ๋ง๊ณ ๋„ ๋ณต์‚ฌ ์ƒ์„ฑ์ž ๊ฐ™์€ ๊ฒฝ์šฐ์—๋Š” ๋‹จ์ˆœํžˆ Form ํด๋ž˜์Šค์˜ ์ƒ์„ฑ์ž๋ฅผ ํ˜ธ์ถœํ•˜๊ธฐ๋งŒ ํ•ด๋„, ๋ฉค๋ฒ„ ๋ณ€์ˆ˜๋“ค์˜ ๋ณต์‚ฌ๋ฅผ ๋งŒ๋“ค์–ด ๋‚ผ ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ P ํด๋ž˜์Šค์—์„œ๋Š” ์ถ”๊ฐ€์ ์ธ ์ฝ”๋“œ ์ž‘์„ฑ ์—†์ด ๋งˆ์น  ์ˆ˜ ์žˆ๋‹ค.

Random

C ์–ธ์–ด ์Šคํƒ€์ผ์„ ์ง€์–‘ํ•˜๋ผ๊ณ  ํ–ˆ์ง€๋งŒ, <random>์€ C++11๋ถ€ํ„ฐ ์ง€์›ํ•œ๋‹ค. ๋”ฐ๋ผ์„œ Module 01์—์„œ ๊ตฌํ˜„ํ•œ ๊ฒƒ์ฒ˜๋Ÿผ ์ง์ ‘ Random ํด๋ž˜์Šค๋ฅผ ๋งŒ๋“ค๊ฑฐ๋‚˜, C ์–ธ์–ด์—์„œ ์ง€์›ํ•˜๋Š” srand ๋ฐ rand ํ•จ์ˆ˜๋ฅผ ํ™œ์šฉํ•˜๋ฉด ๋œ๋‹ค.

Multiline String Literal on std::string

S ํด๋ž˜์Šค์˜ execute๋ฅผ ์ •์˜ํ•˜๊ธฐ ์œ„ํ•ด์„  ์ˆฒ์œผ๋กœ ๋ณด์ผ ์ˆ˜ ์žˆ๋Š” ๋‚˜๋ฌด๋“ค์„ ASCII-Art๋กœ ์ž‘์„ฑํ•ด์•ผ ํ•˜๋Š”๋ฐ, ์ด๋ฅผ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•ด ์ผ์ผ์ด std::cout << ํ˜น์€ std::string์˜ operator+=๋ฅผ ์ด์šฉํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ๋– ์˜ฌ๋ฆด ๊ฒƒ์ด๋‹ค. C++11์—์„œ๋Š” Raw Literal์„ ์ œ๊ณตํ•˜๊ธฐ ๋•Œ๋ฌธ์— Multiline String์„ ์‰ฝ๊ฒŒ ์ž‘์„ฑํ•  ์ˆ˜ ์žˆ๋Š”๋ฐ, C++98์—์„œ๋„ ์ด์™€ ๋น„์Šทํ•˜๊ฒŒ ์ž‘์„ฑํ•˜๋Š” ๊ฒƒ์ด ๊ฐ€๋Šฅํ•˜๋‹ค. ์ด ๋ฐฉ๋ฒ•์€ std::string์˜ operator= ํ˜น์€ ์ƒ์„ฑ์ž๋ฅผ ์ด์šฉํ•œ ๋ฐฉ์‹์ด๊ณ , ๋งค๋ฒˆ operator+=๋ฅผ ํ˜ธ์ถœํ•˜๋˜ ๋ฐฉ์‹์—์„œ ํƒˆ์ถœํ•  ์ˆ˜ ์žˆ๋‹ค.
std::string shrubbery = " ,@@@@@@@,\n" " ,,,. ,@@@@@@/@@, .oo8888o.\n" " ,&%%&%&&%,@@@@@/@@@@@@,8888\\88/8o\n" " ,%&\\%&&%&&%,@@@\\@@@/@@@88\\88888/88'\n" " %&&%&%&/%&&%@@\\@@/ /@@@88888\\88888'\n" " %&&%/ %&%%&&@@\\ V /@@' `88\\8 `/88'\n" " `&%\\ ` /%&' |.| \\ '|8'\n" " |o| | | | |\n" " |.| | | | |\n" " \\\\/ ._\\//_/__/ ,\\_//__\\\\/. \\_//__/_";
C++
ํฅ๋ฏธ๋กญ๊ฒŒ๋„ ์œ„์™€ ๊ฐ™์€ std::string์„ ์ •์˜ํ•  ์ˆ˜ ์žˆ๋‹ค. ์—ด์‹ฌํžˆ " ์Œ์„ ๋งž์ถฐ๋ณด๊ณ  ์žˆ๋‹ค๋ฉด, ์œ„ ํ• ๋‹น์ด ์‚ฌ๋ญ‡ ์–ด์ƒ‰ํ•˜๋‹ค๋Š” ๊ฒƒ์„ ๋Š๋‚„ ์ˆ˜ ์žˆ๋‹ค. ํ•˜์ง€๋งŒ ์œ„ ๊ตฌ๋ฌธ์€ ์ •์ƒ์ ์ธ ๊ตฌ๋ฌธ์ด๋‹ค. ์ปดํŒŒ์ผ๋Ÿฌ๋Š” ํ”„๋กœ๊ทธ๋žจ์„ ๋งŒ๋“ค์–ด ๋‚ผ ๋•Œ ๋ฌธ์ž์—ด ๋ฆฌํ„ฐ๋Ÿด์œผ๋กœ ์ž‘์„ฑํ•œ ๋ถ€๋ถ„๋“ค์˜ ํŒŒ์‹ฑ๋„ ๋‹น์—ฐํžˆ ์ˆ˜ํ–‰ํ•˜๋Š”๋ฐ, ์ด ๋•Œ ์ฝ”๋“œ ์ƒ์— ์—ฐ์†ํ•ด์„œ ๋ถ™์€ ๋ฌธ์ž์—ด ๋ฆฌํ„ฐ๋Ÿด์€ ํ•˜๋‚˜์˜ ๋ฌธ์ž์—ด ๋ฆฌํ„ฐ๋Ÿด๋กœ ํŒŒ์‹ฑํ•˜๊ฒŒ ๋œ๋‹ค. ๋”ฐ๋ผ์„œ ์œ„์™€ ๊ฐ™์€ ๊ตฌ๋ฌธ์„ ์ •์ƒ์ ์œผ๋กœ ์ธ์‹ํ•  ์ˆ˜ ์žˆ๋Š” ๊ฒƒ์ด๋‹ค.

4. ex03 (At least this beats coffee-making)

Intern such as Factory

Intern ํด๋ž˜์Šค๋ฅผ ์ •์˜ํ•˜๋ฉด ๋˜๊ณ , Intern ํด๋ž˜์Šค๋Š” Form ํด๋ž˜์Šค๋ฅผ ๊ฐ์ฒดํ™”ํ•˜์—ฌ ๋ฐ˜ํ™˜ํ•ด์ฃผ๋Š” ์ผ์ข…์˜ Factory Pattern ์—ญํ• ์„ ํ•ด์ค€๋‹ค. ์ด ๋•Œ ํ•ด๋‹น ๊ธฐ๋Šฅ์„ ์ˆ˜ํ–‰ํ•˜๋Š” makeForm ํ•จ์ˆ˜์˜ Exception์„ ์–ด๋Š ๋ฒ”์œ„์—์„œ ์ฒ˜๋ฆฌํ•  ๊ฒƒ์ธ์ง€ ์ •ํ•  ํ•„์š”๊ฐ€ ์žˆ๋‹ค. makeForm ๋‚ด์—์„œ ์˜ฌ๋ฐ”๋ฅด์ง€ ์•Š์€ ํƒ€์ž…์— ๋Œ€ํ•ด Exception์„ throw ํ–ˆ์„ ๋•Œ, try-catch๋ฅผ ์™ธ๋ถ€์—์„œ ํ•˜์—ฌ makeForm์„ ์ฆ‰์‹œ ๋ฒ—์–ด๋‚˜๋„๋ก ์งœ๋Š” ๊ฒƒ๋„ ๊ฐ€๋Šฅํ•˜๊ณ , try-catch๋ฅผ makeForm ๋‚ด์—์„œ ํ•˜์—ฌ ๋ฐ–์—์„œ๋Š” ๋ฐ˜ํ™˜ ๊ฐ’ ๊ฒ€์ฆ๋งŒ ํ•˜๊ณ  try-catch๋ฅผ ํ•˜์ง€ ์•Š๋„๋ก ์งœ๋Š” ๊ฒƒ๋„ ๊ฐ€๋Šฅํ•˜๋‹ค. ๋‚ด ๊ฒฝ์šฐ์—๋Š” ๋ฐ˜๋ณต์ ์ธ try-catch๋ฅผ ์“ฐ๊ธฐ ์‹ซ์–ด์„œ makeForm ๋‚ด๋ถ€์—์„œ try-catch๋ฅผ ์ ์šฉํ•œ ํ›„, ์™ธ๋ถ€์—์„œ๋Š” ๋ฐ˜ํ™˜ ๊ฐ’์˜ ๊ฒ€์ฆ๋งŒ ๊ฐ„๋‹จํžˆ ํ•ด์ฃผ์—ˆ๋‹ค.

Escape Nested Cases

์„œ๋ธŒ์ ํŠธ์—์„œ ์š”๊ตฌํ•˜๋Š” ๋ฐ”๋Š” ์ง€์ €๋ถ„ํ•œ if๋ฌธ๋“ค์„ ์‚ฌ์šฉํ•˜์ง€ ๋ง๋ผ๋Š” ๊ฒƒ์ด๋‹ค. ์ด๋Š” Module 01์˜ ๋ฉค๋ฒ„ ํ•จ์ˆ˜ ํฌ์ธํ„ฐ๋ฅผ ์ด์šฉํ•œ ๊ฒƒ๊ณผ ๊ฑฐ์˜ ์œ ์‚ฌํ•œ ๊ตฌ์กฐ๋ฅผ ๊ฐ–๋Š”๋ฐ, ์—ฌ๊ธฐ์„œ๋Š” ๊ตณ์ด ๋ฉค๋ฒ„ ํ•จ์ˆ˜ ํฌ์ธํ„ฐ๊นŒ์ง€ ์“ธ ํ•„์š”๋Š” ์—†๋‹ค. 3๊ฐœ์˜ if๋ฌธ๊ณผ ๊ฐ ์กฐ๊ฑด์— ๋”ฐ๋ฅธ ์ฝ”๋“œ๋Š” for๋ฌธ 1๊ฐœ, if๋ฌธ 1๊ฐœ, switch 1๊ฐœ๋กœ ๋Œ€์ฒด๋  ์ˆ˜ ์žˆ๋‹ค. ์ถœ๋ ฅ ๋ฌธ๊ตฌ๊นŒ์ง€ ๊ณ ๋ คํ•˜๋ฉด ์ง€์ €๋ถ„ํ•œ if๋ฌธ๋“ค ๋ณด๋‹ค๋Š” ๋” ๋‚˜์€ ๊ฒฐ๊ณผ๋ฅผ ๋ณด์ธ๋‹ค.

5. Code of Jseo