Question Driven Thinking - 스스로 질문하며 학습하기
    에세이

    Question Driven Thinking - 스스로 질문하며 학습하기


    처음 프로그래밍을 배우던 시절을 떠올려보자. 아닌 사람도 있겠지만 대부분의 사람들은 처음 프로그래밍을 배울 때 학교나 학원에서 누군가에게 가르침을 받으며 공부했을 것이다. 프로그래밍을 처음 접하는 입문자에게 독학의 길은 너무 멀고 험난하기 때문이다.

    그러나 입문자 시절이 끝나고 개발자로써 취업도 하고나면 이야기는 달라진다. 이제는 나를 가르쳐줄 선생님이 없기 때문에 스스로 나의 실력을 키워나가야하는 상황이 되어버린 것이다. 이런 환경 속에 갑자기 놓인 사람들은 다시 프로그래밍을 처음 시작할 때처럼 막막한 기분이 든다.

    unnamed

    주변 사람을 붙잡고 물어보기는 하지만 그것도 하루이틀이지, 비슷한 수준의 질문을 계속 하게된다면 돌아오는 것은 RTFM(Read the fucking menual)이나 구글링을 해보라는 냉랭한 대답 뿐일 것이다. 그렇다고 구글링을 하자니 어떤 키워드로 검색을 해야하는지 조차 막막하다.

    이런 경험은 개발자라면 누구든지 겪어보았을 것이라고 생각한다. 공부해야할 것은 산더미이지만 뭐부터 공부해야할지, 어떻게 공부해야할지도 감이 안 오는 상황말이다. 누군가 친절하게 커리큘럼을 짜주는 것도, 알려주는 것도 아니다. 결국 나 스스로 정보를 찾아내고 골라내어 씹어먹어야하는 것이다.

    현실부터 한번 보자

    본격적인 이야기에 들어가기에 앞서 도대체 이 “막막한 기분”이 정확히 뭔지 한 번 짚고 넘어가자. 이 기분을 만드는 것은 그렇게 어렵지 않을 것 같다. 필자는 프론트엔드 개발자이니, 간단한 웹 프론트엔드 어플리케이션을 만들어야하는 상황을 한번 가정해보도록 하겠다.

    우선 뷰와 모델을 연동하여 UI를 그려줄 라이브러리나 프레임워크를 선택해야한다. 이 역할을 하는 도구 중 유명한 것은 React, Vue, Angular 정도가 있겠다. 일반적으로는 생태계가 가장 두터운 리액트를 주로 선택하지만, 사실 뭘로 만들든 원하는 기능을 구현하는데는 아무런 문제가 없다.

    그리고 최근의 웹 어플리케이션에서는 클라이언트에게 복잡한 상태 관리 수준을 요구하기 때문에 상태를 수월하게 관리할 수 있는 라이브러리도 선택해야한다. 이 쪽 계열에서 유명한건 Redux, Mobx 정도가 있으니 입맛대로 골라보자. 만약 UI프레임워크로 Vue를 선택했다면 그냥 Vuex를 사용하는 것이 정신 건강에 좋다.

    그리고 복잡한 객체 상태를 관리하려면 불변 상태를 유지하게 도와주는 라이브러리인 ImmutableJSImmer도 사용하면 좋을 것 같다.

    만약 상태 관리 라이브러리로 Redux를 사용한다면 비동기 처리를 도와주는 redux-thunk, redux-saga 등의 미들웨어도 선택해야한다. 아니면 최근 많이 사용하는 RxJS는 어떨까? Redux와 편하게 함께 사용할 수 있도록 redux-observable과 같은 미들웨어로도 제공하고 있다.

    패키지 관리자는 npm이나 yarn 중에 선택해서 사용하면 되고, 유닛 테스트 도구는 Mocha, Jest 중에 고르면 될 것 같다. eslint의 룰은 airbnbstandard 중에 입맛에 맞는 걸로 고르고 적당히 커스터마이징해서 쓰자.

    음, 그리고 생각해보니 자바스크립트보다는 정적 타이핑 언어인 타입스크립트를 사용하는 것도 나쁘지 않을 것 같다. 이왕 만드는 거 조금 더 단단하게 만들면 좋으니까. 그렇다면 위에서 이야기했던 라이브러리들이 타입스크립트를 지원하는지 알아봐야한다.

    what 간단한 어플리케이션 만든다매...?

    방금 이야기한 수많은 도구들은 필자가 잘난척하려고 줄줄 읊어댄 것이 아니라, 실제로 회사에서 일을 하거나 사이드 프로젝트를 진행할 때 프론트엔드 개발자들이 매번 고민하는 것들이다. 물론 저 도구들은 전부 사용해도 되고 안해도 되는 도구들이지만, 사용 방법만 익힌다면 생산성이 훨씬 높아지기 때문에 대부분의 프론트엔드 개발자들은 저 정도는 차려놓고 사용한다.

    그리고 사실 저런 도구들을 제대로 사용하기 위해서는 클로저나 이벤트 루프와 같은 자바스크립트의 디테일한 개념, 가상돔, 데이터 바인딩, MVVM 패턴, Flux 패턴, 함수형 프로그래밍 등에 대한 지식도 필요하다.

    최근 들어 프론트엔드 분야에 유독 새로운 게 많이 나오기는 하지만, 다른 직군의 개발자들도 알아야하는 지식의 양은 대부분 비슷비슷하다. 다만 각 직군에 맞게 특화되어 있을 뿐이다.

    사실 이 길고 긴 이야기를 통해 필자가 하고 싶은 말은 딱 이거 하나다.

    “이 많은 걸 친절하게 다 알려줄 수 있는 사람은 없다.”

    결국 정보는 스스로 찾아야한다

    저렇게 많은 것을 다 알려줄 수 있는 사람이 과연 존재할까? 개인적으로 필자는 없을 것이라고 본다.

    만약 수학처럼 100년 전에 누군가 만든 공식이 100년 후에도 그대로 사용되는 학문이라면 누군가 체계적인 커리큘럼을 만들어서 저런 것들을 모두 가르쳐줄 수 있을지 모르지만, 필자가 이야기했던 저 도구들 중 많은 수는 당장 내년이 되면 사라질 수도 있는 녀석들이다. 즉, 지식의 생명이 굉장히 짧다는 것이다.

    그리고 같은 역할을 하는 저 많은 도구들 중에서 뭐가 더 좋고 나쁘고를 가리기도 애매하다. 당장 근처에 있는 프론트엔드 개발자에게 React가 좋아? Vue가 좋아?라고 물어본다면 뭐라고 대답할까? 아마 둘 다 좋다거나 둘 다 구리다거나, 아니면 자기 맘에 드는 것 하나를 골라서 이야기할 것이다.

    그런 이유들 때문에 프로그래밍은 특정한 커리큘럼을 만들기가 꽤나 어려운 분야이다. 물론 처음 프로그래밍을 배우는 단계에서는 커리큘럼을 어느 정도 만들어줄 수 있지만, 나중에 가면 사실 커리큘럼이라는 것 자체가 별로 의미가 없다.

    기껏 학원에서 3개월동안 열심히 Vue를 학습했는데 막상 이직한 직장은 React를 쓰고 있다면 어떻게 할 것인가? 그렇다고 회사에 양해를 구하고 학원에 가서 React를 3개월 동안 다시 배울 수는 없는 노릇이다.

    결국 개발자들은 속해있는 조직의 상황이나 배우고 싶은 기술 등에 맞춰서 자신에게 필요한 정보들을 스스로 찾아서 학습해나가는데 익숙해질 수 밖에 없고, 그래서 개발자들에게 뭔 질문만 했다하면 구글링을 해보라는 대답이 돌아오는 것이다.

    하지만 구글이나 스택오버플로우에서 정보를 스스로 찾아 주워먹는 식의 능동적인 학습을 하기 위해서는 적절한 키워드를 선택하여 구글링을 할 수 있는 능력과 좋은 정보와 나쁜 정보를 가릴 수 있는 식별력까지 겸비해야 올바른 정보를 주워먹어가며 학습할 수 있기 때문에 생각보다 쉽지 않다. (영어도 잘 해야 한다) 게다가 이건 누가 알려줄 수 있는 것도 아니라서 스스로 연습하고 연구해야한다.

    하지만 당장 구글에 뭘 검색해야할지, 뭘 공부해야 좋을 지도 모르겠는데 무작정 구글링을 하라고 할 수는 없는 법이니 필자가 자주 사용하는 아주 간단한 방법을 한번 공유해보려고 한다.

    모든 키워드는 연결되어 있다

    우리는 보통 공부를 할 때 “암기”를 한다. 암기를 통한 학습은 좁은 폭의 정보를 빠르게 습득할 수 있게 해주기 때문에 늘 새로운 트렌드에 쫓기며 사는 개발자들에게는 꽤나 잘 맞는 학습 방법이라고 할 수 있다.

    뭐, 순수 함수의 특징 4가지를 외운다던가, TCP나 UDP의 특징과 장단점을 외운다던가 하는 것들 말이다. 또는 새로운 라이브러리나 프레임워크가 나오면 공식 문서를 한번 쭉 흝어보고 코딩을 해보며 연습하는 것도 일종의 암기라고 할 수 있다.

    그러나 이런 단순 암기를 통한 학습 방법은 빠르다는 장점도 있는 반면, 학습 키워드의 습득이 단편적이라는 단점도 가지고 있다. 키워드의 습득이 단편적이라는 말은 어떠한 키워드를 습득했을 때 자연스럽게 다음 레벨의 키워드로 연결되기가 어렵다는 말이다. 아마 이렇게 공부를 하다보면 어느 순간 이런 생각이 들 때가 있었을 것이다.

    budda 좋아... 여기까진 완벽해... 근데 다음엔 뭘 공부해야하지...?

    분명히 머리로는 내가 공부한 것들이 아직 한참 모자라다는 것을 알고는 있지만 그 다음에 뭘 공부해야하는지도 모르겠고, 그렇다고 전혀 다른 키워드를 찾아서 공부하기에는 괜히 여기저기 찔러보기만 하는 것 같은 기분 말이다. 이는 단순한 암기를 통해서 학습한 지식들이 서로 “연결”되지 않았기 때문에 나타나는 현상이다.

    사실 지식이라는 것은 일종의 키워드 마인드맵이라고 할 수 있으며, 마인드맵 안에 있는 모든 키워드는 밀접하게 관련이 있는 다른 키워드들과 연결되어 있다. 결국 능동적인 학습은 이렇게 연결된 키워드를 찾아나서는 탐구 과정의 연속이라고 할 수 있다.


    단순 암기를 통한 학습은 이 마인드맵의 키워드 하나하나를 직접 찾아내어 학습하는 것이다. 그러나 저 많은 키워드들을 스스로 전부 찾아내어 공부한다는 건 꽤나 어려운 일이다. 그래서 우리는 하나의 키워드를 공부하며 그 속에서 자연스럽게 다음 키워드를 찾아낼 수 있는 방법을 생각해야한다.

    그리고 이렇게 하나의 키워드에 대해서 학습하며 다음 키워드를 찾는 행위를 반복하다보면 단순 암기를 통해 저장했던 파편적인 정보들 간의 연결고리도 자연스럽게 생성되기 때문에 더 기억이 오래가는 효과도 누릴 수 있으므로 일석이조의 효과를 누릴 수도 있다.

    그렇다면 어떤 과정을 통해 연결된 키워드를 찾아낼 수 있을까?

    스스로에게 질문을 던져보자

    우리가 어떤 주제에 대해서 공부하면서 연관된 키워드를 찾아내지 못하는 이유 중 하나는 그저 암기를 통해 정리되어있는 지식을 받아들이기만 한다는 것에 있다. “A는 B다”라고 외우기만 한다면 그 속에 숨어있는 다른 키워드들을 찾을 기회조차 놓치게 되어버리는 것이다.

    필자가 제시하는 방법은 바로 “질문”이다. 단, 이 질문은 남들에게 질문하는 것이 아니라 스스로에게 하는 질문이다. (남들에게 질문하는 것은 가장 최후의 보루로 남겨놓도록 하자)

    스스로에게 “왜 이렇게 되는데?”, “어떻게 이게 가능한데?”와 같은 질문을 던지며 공부하고 있는 키워드에 대해서 자신이 모르는 것이 무엇인지 하나씩 찾아가는 것이다. 그리고 자신이 모르는 것이 무엇인지 알았다면 이제 구글링을 통해 그 질문에 대한 답을 찾아보면 된다. 이렇게 몇 번 반복하다보면 아마 그 질문에 대한 답을 쥐고 있는 새로운 키워드를 찾아낼 수 있을 것이다.

    리액트 훅의 useState를 한번 예로 들어보겠다. 리액트의 useState는 함수형 컴포넌트에서 상태를 저장하고 기억하고 싶을 때 사용하는 훅이다.

    function Foo () {
      const [count, setCount] = useState(0);
      return (
        <>
          <div>{count}</div>
          <button onClick={() => setCount(count++)}>+</button>
        </>
      );
    }

    사실 useState라는 훅을 사용하면 함수형 컴포넌트 내에서 상태를 관리할 수 있다는 사실만 알고 있어도 코딩을 하고 어플리케이션을 만드는 데에는 아무 지장이 없고, 시간에 쫓기는 학습을 해야하는 상황이라면 이쯤에서 학습을 접고 코딩을 해도 된다. 그러나 단지 useState 훅을 사용할 수 있다는 사실만으로 만족할 수 없다면 이쯤에서 새로운 질문을 하나 던져봐야한다.

    필자는 처음 리액트의 함수형 컴포넌트를 접하고 이 훅을 알게 되었을 때 이런 원초적인 궁금증이 들었었다.

    useState 훅은 어떻게 상태를 저장할 수 있는걸까?

    사실 이런 질문은 그렇게 대단한 질문도 아니다. “useState 훅을 사용하면 함수형 컴포넌트 안에서도 상태를 저장할 수 있다”는 단순한 암기에서 조금만 더 호기심을 가지고 앞으로 나아갔을 뿐이다.

    물론 보자마자 useState 훅의 원리를 바로 알 수 있을 정도로 자바스크립트에 대한 지식이 많은 분이라면 질문의 난이도도 더 높았을테지만, 당시 필자는 이 훅의 원리에 대해 전혀 감을 잡지 못했었다.

    자, 어쨌든 이렇게 스스로 질문을 했으니 이제 답을 찾아야한다. 당연히 이 질문에 답해줄 수 있는 선생님은 내 곁에 없으니 갓 구글에 이 질문을 그대로 검색해보도록 하자.

    필자가 선택한 검색 키워드는 useState 원리이다. 검색 키워드를 바꿔서 재시도한다고 과금되는 것도 아니니 그냥 손 가는대로 마음 가는대로 때려넣어보자. 사실 구글링에 무슨 대단한 스킬이 필요한 것도 아니다.

    googled 역시 구글신께서는 모든 걸 알고 계신다

    구글에 해당 키워드를 검색해보니 이미 다른 분들이 리액트 훅에 대해 자세히 정리해놓은 포스팅들이 보인다. 만약 한글로 구글링을 진행했는데 원하는 자료가 나오지 않는다면 Principle of useState와 같은 영어 키워드로 다시 한번 검색해보면 대부분 원하는 자료를 찾아낼 수 있다. 사실 한글로 검색했을 때와 영어로 검색했을 때 찾을 수 있는 정보량의 차이는 어마무시하기 때문에 되도록이면 영어로 검색하는 습관을 들이는 것이 좋기는 하다.

    사실 리액트의 useState 훅은 자바스크립트 클로저의 성질을 이용하여 함수 내부에 상태를 저장할 수 있도록 만든 것이기 때문에 조금만 검색해보면 여러분은 클로저(Closure)라는 키워드를 얻어낼 수 있다.

    이렇게 클로저라는 새 키워드를 얻었을 때 여러분이 클로저가 무엇인지 안다면 useState 훅을 직접 만들어 보며 공부해봐도 좋고, 아니면 다른 질문을 던져서 다시 새로운 키워드를 찾으면 된다.

    만약 클로저가 무엇인지 잘 모른다면 자바스크립트 클로저와 같은 검색 키워드로 다시 구글링해서 해당 내용에 대한 학습을 진행하면 된다. 아마 클로저를 공부하다보면 또 다른 질문을 던져볼 수 있을 것이고 그로 인해 더 깊숙한 곳에 있는 새로운 키워드를 또 찾을 수 있을 것이다.

    이 글을 읽으신 독자분들께서는 “당장 공부하고 사용하기만 해도 벅찬데 더 어려운 원리를 언제 다 이해해?”라고 생각할 수도 있겠다. 그러나 “키워드를 이해할 수 있는 능력”과 “키워드를 찾을 수 있는 능력”은 엄연히 다르다는 것을 알아야한다.

    애초에 키워드를 이해할 수 있는 능력은 사실 몇 개의 팁만으로 단기간 안에 키울 수 있는 능력이 아니다. 어떤 분야의 키워드를 빠르게 이해할 수 있는 능력은 일정 수준 이상의 해당 분야 지식을 기반으로 하기 때문이다.

    하지만 “키워드를 찾을 수 있는 능력”은 다르다. 딱히 일정 수준 이상의 지식이 필요한 것도 아니고, 그저 구글에 검색어를 칠 수 있는 손가락만 있으면 된다. 그리고 만약 새로운 키워드를 획득했는데 이해하기가 너무 어렵다고 느껴진다면 굳이 바로 학습하지 않아도 된다.

    키워드를 획득한다는 것이 가지는 가장 작은 의미는, 적어도 “세상에 이런 것도 존재하는구나”라는 정도의 지식은 얻을 수 있다는 것이다. 이런 키워드가 존재한다는 것을 알고 있다면 나중에 자신이 학습한 지식의 깊이가 더 깊어지고나서 그 키워드를 다시 꺼내보면 되는 것이고, 그렇게 학습을 다시 진행하며 다음 키워드를 또 찾아내는 과정을 반복하면 된다. (개발자로 일하다 보면 분명히 언젠가 그 키워드에 대해서 학습해야할 날이 온다)

    마치며

    사실 제목을 Question Driven Thinking이라고 거창하게 쓰기는 했지만, 앞서 말했듯이 이렇게 질문을 통해 지식을 습득하는 학습 방법은 필자가 처음 이야기하는 것이 아니라 꽤나 유명한 학습 방법 중 하나이다.

    이렇게 질문을 통해 조금씩 답을 찾아나가는 방법은 고대 그리스 시절부터 계속 해서 사용해오던 굉장히 유명한 교수법 중 하나이며, 스스로에게 질문을 함으로써 자신이 모르고 있는 것을 계속 해서 찾아나가고 해답을 찾아가는 과정은 과거 소크라테스 형님도 많이 사용하던 방법이었다.

    socrates 내가 아무것도 모른다는 것을 안다는 것이 제일 현명한 것이라는 띵언을 남기신 형님

    사실 우리는 어릴 때부터 교과서에 나오는 수학 공식, 영어 단어, 시험문제 유형 같은 것들을 달달 외우는 학습을 거의 10년 동안 받아왔기 때문에 단순 암기하는 학습에 더 익숙하다. 오히려 학교에서는 질문을 하면 괜히 수업시간 더 길어지게 만드는 이상한 놈 취급을 받기 일쑤였던 것 같다. (나대는 놈이라는 칭호도 함께 얻을 수 있다)

    하지만 단순히 “왜?”라는 질문을 던짐으로써 “A는 B다”라고 기억되던 평면적인 지식을 “A는 ~기 때문에 B다”와 같은 심층적인 지식으로 바꿀 수 있기 때문에 우리는 이제 질문에 익숙해져야한다. 질문을 던지며 내가 모르는 것이 무엇인지 찾아내고 그 질문에 대한 해답을 찾아내어 다시 대답하는 과정을 반복하며 키워드를 계속 만들어나가는 것이다.

    그리고 스스로에게 질문을 하게 되면 생각에 생각이 계속 해서 꼬리를 물며 깊어질 수 있기 때문에, 공부할 때 뿐만 아니라 생각을 정리할 때도 좋은 방법이므로 한번쯤 도전해보는 것을 권한다.

    이상으로 Question Driven Thinking 포스팅을 마친다.

    Evan Moon

    🐢 거북이처럼 살자

    개발을 잘하기 위해서가 아닌 개발을 즐기기 위해 노력하는 개발자입니다. 사소한 생각 정리부터 튜토리얼, 삽질기 정도를 주로 끄적이고 있습니다.