내맘대로 정의하는 디자인 패턴! 디자인 패턴이란 무엇인가?

안녕하세요. 연두아빠에요.


앞으로 시간 날 때마다 디자인 패턴에 대해 복습하고 공부도 하며 스터디 노트를 올려볼까 합니다.


디자인 패턴에 대해 본격적으로 공부하기에 앞서 디자인 패턴이란 뭔지에 대해 되집어 보고 싶네요.



혹시, 군맹무상(群盲撫象)이라는 고사성어 들어보셨나요?


여러 명의 장님이 코끼리를 어루 만진다는 뜻입니다. 흔히 속담으로 장님 코끼리 만지기라고도 하는...


장님처럼 평생 앞을 보지 못했던 사람이 코끼리를 어루 만지면 코끼리의 형태를 짐작하기 쉬울까요?


이렇듯 식견(識見)이 좁은 사람이 자기 주관대로만 사물을 판단하는 경우를 비유하는 말입니다.



갑자기 고사성어 얘기를 한것은 디자인 패턴에 대해 저 나름의 간단한 정의를 내려보고자 해서였습니다.


게임을 만들다 보면 수많은 고민을 하게 되고 하루에도 수백번 구글링을 하며 필요한 기법들을 검색하곤합니다.


진짜 실력자는 안찾아보고 달달 외워서 막 코딩해 나가는 사람이다? 저는 그건 아니다 라고 감히 말씀드리고 싶네요.


저는 좋은 게임을 만드는 프로그래머에게 가장 필요한 요소는 넓고 얕은 지식이 아닐까 생각합니다.


물론 우리의 궁극적인 목표는 넓고 깊은 지식을 가진 사람이 되어야 하겠지만요^^



게임 개발 경험이 있으신 분들이라면, 맨땅에 헤딩을 3박 4일 해도 답이 안나오던 경험들이 있으셨을 겁니다.


그때 마다 저에게 간절하게 들던 생각은 단 하나였습니다.

아오... 누가 힌트라도 줬으면...

힌트! 예전에 고등학생 시절 PC통신에 한참 게임을 만들어서 올리며 명성을 올리고 싶어 발악을 하던 시절...


오락실에 있는 땅따먹기 게임을 도대체 어떻게 만들어야 할까? 막 아무렇게나 영역을 설정하면 그림이 오픈되고...


겁나 신기하네... PC 통신 시절이니 책과 동호회에 질문 하는 방법 밖에 지식을 얻을 방법이 없었던 그 시절...


거의 몇날 며칠을 고민하고 안돌아가는 머리를 굴리며 나름의 방법을 짜내기 위해 이것 저것 시도해 보다가

폐곡선!

당시에 제가 뭐라고 질문을 올렸고, 누가 뭐라고 대답을 해주셨는지는 정확히 기억도 안납니다.


몇 번을 질문을 올렸지만, 며칠째 답을 해주시는 분은 없었고, 그러다 정말 짧게 달렸던 그 답변!


기억나는 것은 폐곡선이라는 키워드 하나였습니다.



폐곡선이 뭐지? 라는 궁금증으로 PC통신과 MSDN을 쥐잡듯이 뒤지며 검색을 하다가


드디어 일주일만에 내가 선택한 영역을 까맣게 칠해주는 샘플 코드를 만들어 내게 되었습니다.


내가 먹은 땅은 까맣고, 내가 먹지 않은 땅은 하얀색인데 여기에 그림 파일 하나 가져다 놓고 마스킹 처리하니


땅따먹기가 만드는 것도 별거 아니구나 룰루 랄라~



지금 생각해보면 굳이 폐곡선을 찾지 않더라도 다른 방법으,로 구현할 수도 있을 것 같긴 합니다만...


그런 것을 구현해 냈다는 것 만으로도 한 두세달은 엄청 뿌듯해 했던 기억이 새록새록 나네요.



뭐... 지금 땅따먹기 관련해서 얘기를 하자는 건 아니고...


이렇게 게임을 개발하다 벽에 부딪혔을 때 어떻게든 답을 찾을 수는 있을 거라고 생각합니다.


폐곡선이라는 키워드를 아무도 말해주지 않았다고 해도 결과는 둘 중 하나였을 겁니다.


땅따먹기는 아직 나에게 무리니 포기하자 혹은 어떻게든 만들어 보자 야메 땅따먹기


하지만 폐곡선이라는 힌트를 바탕으로 그 후의 일들이 술술 풀려나가며 쉽게 개발할 수 있었습니다.



그러나 소프트웨어를 설계하며 봉착하는 문제에 해당하는 답이 단 하나 밖에 존재하지 않는 경우는


극히 드물었던 것 같습니다. 어떤 문제던 해결을 위한 다양한 방법들이 존재하죠.


그러나 그 문제를 풀기 위한 최적의 기법들은 늘 1~2가지로 축약되는 경우가 대부분입니다.


서론이 길어지는 것 같은데 잽싸게 정리해보면 제가 말하고자 하는 요지는 다음과 같습니다.

내 맘대로 만들어도 만들 순 있다.

하지만 더 나은 방법은 분명 존재한다.

최적의 방법으로 만들어야 최적의 프로젝트가 나오겠죠.


서울에서 부산 가는 방법이야 수십, 수백가지가 있을 수 있겠지만 기왕이면 편하게 오는게 좋지 않을까요?


자기 차가 있다면, 차로 가는 것도 고민해 볼 수 있을테고. 운전하기 싫고 여유가 된다면 비행기나 KTX도 좋구요.


자금 상황이 여의치 않으면 새마을호, 그 다음으로는 버스나 무궁화호 등의 차선책도 생각해볼 수 있겠네요.


걸어오는 건 제 주머니에 돈이 한푼도 없더라도 고려해보고 싶지 않네요^^;



디자인 패턴은 수 많은 사람들이 소프트웨어 설계 과정에서 얻은 세세한 경험들을 바탕으로 


이런 상황에선 이렇게 설계하는면 편리하고 좋지만, 이러이러한 단점들이 있다와 같이


소프트웨어 설계 과정에서의 여러 상황들에 대한 최적의 해법들을 제시합니다.



소프트웨어를 설계하면서 기반 설계가 제대로 이루어지지 않은 상황에서 수십 개의 클래스들을 마구 만들어 내다보면


결국에는 비슷한 역할을 하는 클래스가 중복이 되기도 하고, 클래스 구조가 얽히고 섥혀 코드는 꼬일때로 꼬이게 되고


이때 등장하는 디자인 패턴이 바로 야메 해결 패턴으로 주로 // HACK: 이라는 주석과 함께 사용되곤 하지요.


한두개의 야메 해결책들은 게임을 개발하며 어느 정도 용납하자라는 주의긴 합니다만...


이런 야매 해결책들이 누더기 처럼 쌓이게 되면, 어떤 슈퍼 프로그래머가 와도 손대기 싫은 코드가 되버리게 됩니다.

나중에 리펙토링 하면 돼!

꼭 저 말을 한 사람에게 그 일을 맡기세요!


1년 만든 게임을 6개월 걸려 리팩토링 할 수 있을까요?


이미 갈 때까지 가버리고, 꼬일데로 꼬여버린 구조를 뒤엎는건 그만큼 큰 비용을 감수해야 하는 일입니다.



혹은 나름 슈퍼 프로그래머라고 불리는 사람이라 하더라도 초기 요구에 맞춰 깔끔하게 만들어 놓은 클래스 구조를


요구 사항이 수시로 바뀌는 것에 일일히 대응하면서도 깔끔한 설계를 유지하는 것은 쉽지 않은 일입니다.



우리가 C++이나 Java와 같은 언어를 공부할 때 가장 먼저 들었던 OOP라는 단어 기억나시나요?


객체 지향 프로그래밍(Object Oriented Programming)


OOP의 추상화, 캡슐화, 상속성, 다형성 4가지의 특징이 있고... 


데이터 은닉과 코드 재활용이 손쉽고 확장성이 뛰어나고...


엄청 좋고 대박 짱인 프로그램 개발 방법!


이 엄청 좋고 대박 짱인 OOP의 특성들을 프로젝트가 끝날 때까지 유지하는게 참 쉽지가 않습니다.


내가 사용하는 언어는 분명 C++이고 C#이고 Java인데... 캡슐화는 개뿔?! 귀찮으니 전부 public으로!


코드 재활용이 뭐죠, 엿바꿔 먹는 건가요? 이 클래스의 확장은 불가능 합니다. 죄송합니다...



이런 말도 안되는 상황을 전 세계 프로그래머들이 공통적으로 경험하고 같이 고민을 하다가


프로그램의 목적이 어떻든 간에 객체 지향의 장점을 유지할 수 있는 최적의 코드를 설계 하기 위한


클래스 구조들 사이에 일정한 패턴이 존재한다는 것을 깨닫고, 이를 디자인 패턴이라 부르게 되었습니다.



정리하면, 디자인 패턴은 결국 이런 이런 상황에선 이런 형태의 클래스 구조를 설계하는 것이 좋고,


이런 장점과 단점을 갖는 다는 선조님들의 지혜들을 기록해 놓은 성서라고 할 수 있습니다.


프로젝트 규모가 커지고 프로젝트에 참여하는 개발자가 바글바글 해질 수록 이런 디자인 패턴에 대해


다들 이해하고 참여를 하게 된다면 아무리 클래스가 많아지더라도 객체 지향의 기본 원칙을 무시하지 않고


효율적인 방식으로 소프트웨어 개발이 가능하게 됩니다...


라고 말하고 있지만, 개발이 완료되는 그 시점까지 유지되는 것은 참 힘들긴 한 것 같습니다.



어쨋든,이러한 디자인 패턴들은 SOLID라고 불리는 다음의 5가지 설계 원칙을 준수해야 합니다.


SRP(The Single Responsibility Principle) : 단일 책임 원칙


어떤 클래스를 변경해야 하는 이유는 오직 하나뿐 이어야 한다.


OCP(The Open-Closed Principle) : 개방-폐쇄의 원칙


클래스나 모듈, 기능들에 있어 확장에 대해서는 Open, 변경에 대해서는 Close.


LSP(Liskov Substitution Principle) : 리스코프 치환 원칙


자식 타입(Sub Type)은 언제나 부모 타입(Base Type)으로 교체할 수 있어야 한다.


ISP(The Interface Segregation Principle) : 인터페이스 분리 원칙


자신이 사용하지 않는 메소드에 의존 관계를 맺어선 안된다.


DIP(Dependency Inversion Principle) : 의존 관계 역전 원칙


고차원 모듈은 저차원 모듈에 의존하면 안된다.


뭐 더 자세하게 정리할 까도 고민 했지만, SOLID 원칙이라고 구글링 해보면 더 자세하게 나오니


꼭 한번 검색해보시고 이해되시는 부분 까지만 이해하시고 넘어가도 큰 도움이 되실거라고 생각합니다.



이 글을 시작으로 디자인 패턴 관련해 개인적으로 복습하고 스터디를 하며 정리해서 포스팅하고자 합니다.


제가 앞으로 올리게 될 글 들은 강좌가 아니고 저의 스터디 노트입니다.


이러한 주제들로 블로깅을 하는 가장 첫번째 이유는 제가 필요할 때 구글보다 먼저 제 블로그에서 대부분의 자료를


검색하고 기억을 되돌아보기 위함입니다.



제 블로그를 찾아주시는 분들도 이러한 취지를 알아 주시고 조금이라도 도움이 되셨으면 좋겠습니다.


제가 올리는 글 들에 문제가 있거나, 잘못 해석한 부분이 있다면, 혹은 오타가 있더라도 지체없이 지적해주시면


빠른 수정으로 보다 정확한 내용을 공유할 수 있도록 최선을 다하겠습니다. 많은 관심과 도움 부탁드립니다^^


공감() 및 댓글은 글쓴이에게 커다란 힘이 됩니다.


길지 않은 이 글을 쓰는데 나름 몇 시간이 걸렸어요^^;


저에게 1초만 시간을 내주셔서 공감 버튼 꾸욱 눌러주세요^^


제 블로그를 방문해 주신 모든 분들 사랑합니다^^


이상입니다. 감사합니다!



이 글을 공유하기

댓글

Designed by CMSFactory.NET