떠먹여 주는 것과 떠먹는 것의 차이
오라클 공인인증센터에서 한 정보보안 전문가 교육과정을 수료하고 케이티-SB(소프트뱅크) 데이터 센터에서 면접을 봤다. 토익 900점 이상의 수재들만 뽑는 서류전형 자격요건을 봐서는 대단한 인재들이 모이겠구나 생각했었다. 필자는 취업알선을 시켜주는 센터의 한 지인의 추천으로 토익 900점대 수준의 회화실력의 소유자라는 이력서를 제출했었다. 그리고 면접을 보고 합격했으나, 막상 들어가니 정보통신 보안 업무는 kt 본사에서 맡고 있었고 그래서 단 이틀만 있다가 나왔다(삼일 째 그 근처 카페로 출근했다;). 면접 시 나에게 여러 질문을 하였으나, 막바지에 영어로 취미를 말해보라고 해서 본인은 일전에 헬스장에서 웨이트 트레이너를 해본 경험도 있어서 어떻게 운동을 하며 식단을 짜야하는지 잘 알고 있으며, 기회가 된다면 면접관들의 다이어트를 책임져주겠다고 시원하게 영어로 답변했었다. 그러니깐 토익 900점대의 수준이 나의 영어 말하기 수준으로 얼추 커버가 되어서 뽑혔구나 했는데, 막상 본인의 하고자 한 보안과 관련된 일을 하는 곳이 아니었다.
그 당시 수료한 교육과정에 이어서 한창 정부기관에서 웹사이트 구축 시에 권장한 Spring 프레임 워크와 JSP 개발과 관련된 교육과정을 어느 한 대학교에서 듣고 있었다. 그래서 앞서 본 면접과 일하러 간 며칠이 교육과정에서 여간 아까운 게 아니었다. 그렇다고 소개를 시켜준 지인의 제안을 거절할 수도 없는 노릇이었고 어이됐든 개발과정에서 하루, 이틀을 건너뛰면 빠진 수업내용은 알아서 메꿔야 했기 때문에 도통 수업 따라가는 게 힘든 게 아니었다. 더군다나, 당시 정보보안 산업기사를 합격한 후 보안 기사 필기를 다시 준비하고 있었기 때문에 수험 준비하느라 수업내용 환기하느라 여간 갈피를 잡기가 힘들어서 아예 하나에 매진했다. 그래서 개발은 백앤드로 자칭해서 같은 프로젝트 팀을 이룰 애들의 인프라 구축을 염두에 두었다.
당시에 정작 확실하게 개념을 파악해야 했을 자바, 자바스크립트, 제이쿼리나 뭐 JSP(스프링 프레임워크까지 이해하기 위해 그 대학교 도서관에서 신간 서적으로 리뷰도 해보았으나...)는 수업시간에만 듣고 강의 시 강조하는 부분만 메모해두고, 오로지 정보보안기사에만 올인했었다. 어쨌든 그 후 보안기사를 실기까지 합격하고 초기 보통의 개발자의 대우보다 좋게 어느 지방의 공공기관에서 보안과 관련된 일을 하게 되었지만, 이때에 개발에 대해서 기초를 좀 더 심도 있게 다지지 못한 게 여간 아쉬운 게 아니었다. 실무진의 얘기로는 어차피 진정한 개발 실력은 개발자가 되고 나서야 는다고 하니 교육기간 동안 알아듣지 못한 개념에 대해서 아쉬워할 것도 아니지만 말이다. 그리고 또한 나이 마흔이 다돼가면 관리자나 영업으로 뛰어야 하는 게 한국의 개발자 현실인데, 개발자로 취업해봤자 몇 년을 할 수 있을지도 몰랐다. 하지만 어느 책에서 보기로는 나이 마흔을 넘겨서 시작한 비전공자 출신의 개발자도 아직도 개발을 하고 있다(물론 학벌빨이겠지만...)는 문구를 보고 개발자(선진국에서는 코더 수준의 개발직종은 저임금 국가로 아웃소싱하고 있는 추세에도 불구하고...)에 대한 미련을 버릴 수 없었다. 아니, 정확하게는 뭔가 새로운 것을 스스로 개발할 수 있는 개발자 낭만이다. 하지만 개발의 90%는 창의력이 개입할 필요가 없단다.
본인의 브런치 프로파일을 보면, 분해(Decomposition), 일반화(Generalization), 추상화(Abstraction), 그리고 알고리즘(Algorithm)에 천부적이라는 PR를 볼 수 있다. 이것 외에 패턴화(Patterning)까지 포함하면 컴퓨팅 사고에서 가장 중요한 요소를 나타내는 개념들이다. 앞으로 AI가 대처하는 능력의 핵심이 이 다섯 가지의 기술들이고, 이것이 사실 개발자가 프로그램을 만들 때 가장 기본으로 사고할 수 있어야 하는 과정이다. 그런데 이것들을 찬찬히 뜯어보면 어릴 적에 누구나 한 번 만져본 레고(LEGO)의 조립과 똑같다는 것을 알 수 있다. 어릴 때 본인은 처음 레고를 사면, 일단 조립 매뉴얼을 보고 그대로 따라 만들기를 밤새도록 한다.
하지만 여기서 끝나는 게 아니다. 레고 조립에 어지간한 흥미가 붙으면 이제 응용 단계로 나아간다. 이 시리즈 저 시리즈 각종 테마 시리즈가 섞여 있는 집안의 모든 레고 블록들을 재료 삼아서 이제 자기만의 상상의 완성체를 만들기 시작하는 것이다. 그러면 이미 머릿속에서 상상의 최종 구현물을 그리므로 이것을 '추상화'의 시작이라고 말할 수 있다. 왜냐하면 이것은 처음 레고를 샀을 때 포장지 겉면의 사진대로의 완성된 레고 조립품을 기대하고 조립하는 게 아니라, 본인이 무엇을 만들겠다는 추상적인 개념만을 가지고 시작하기 때문이다. 그리고 기존의 매뉴얼을 보고 따라서 만든 조립의 과정(기존의 '알고리즘')이 손에 익어 있으므로 이것을 바탕으로 새로운 조립을 시작한다. 새로운 조합으로 다시 완성된 나만의 작품을 나름의 호칭으로 이름 지어('일반화') 준다. 그리고 며칠 지나서 이것이 싫증 나면 다시 '분해'하고 재조립하기를 반복한다.
레고라는 창의적인 놀이의 시초는 덴마크에서 개발되었지만, 세상의 모든 아이들이 레고를 통해 새로운 조립(조합)을 완성하고 분해함으로써 사실 컴퓨팅 사고의 기초 발판을 닦은 것이었다. 그러므로 어릴 적 반드시 레고만이 아니라 이런 조립식 블록의 장난감을 한 번이라도 만져본 아이라면 어쩌면 개발자로서 기본적으로 갖추어야 할 컴퓨팅 사고는 이미 해봤다고 말할 수 있다. 본인은 이 레고를 나만의 상상의 나래를 통해 재조합하는 데는 한 일가견이 있었다고 말할 수 있다. '그래서 뭐?'라고요? 자바스크립트를 지금 와서 이 마당에 다시 환기하는 데 어려움은 없었다는 거다. 개발자 교육 과정 당시의 한 강사님이 비록 개념만 신나게 잡아주고(이때만 열성적으로 강의하는 모습이었다), 강사 본인이 타이핑한 코드에 대해서는 대강 설명해주어서 당시에 함께 수업을 들은 얘들의 수료 후 강의 평가를 보면 음...(개인적으로 개념 위주의 강의법을 더 좋아한다. 실습은 어차피 나름 터득해야 하지 않는가...)
나는 어쨌든 따라서 타이핑하기에 바빠서 코드 문법에 대한 하나하나에 대한 이해는 기대도 안했지만, 자바의 객체지향적인 특성에 따른 함수 호출의 이해만큼은 확실히 했었다. 그리고 지금 와서 그 당시 강사가 휘리릭 타이핑하고 화면을 넘겼던 것으로 기억하는 자바스크립트의 내용을 환기해보니, 별 것도 아니었던 거다. 개념이해가 수월해졌다는 말이지, 책의 소스 코드를 안보고 술술 타이핑할 수 있다는 뜻이 아니다. 당시의 말씀대로 개발 문법에 대한 이해나 숙련도는 시간이 지나면 누구나 다 알게 된다는 것이 틀린 말이 아니구나를 실감하는 중이다.
그래서 『하버드 상위 1퍼센트의 비밀』라는 책에서 언급한 이 긴 '간격 효과'를 도움받아서 만든 게 ‘Coffee Order'라는 로직 구현물이다. 소스 코드는 Github 사이트의 본인의 Repository에서 다운로드할 수 있으며, 이번 섹션의 목적은 자바 스크립트의 프로토타입(prototype, 조립품(새로운 객체)이 생성되기 이전의 뼈대에 해당하는 초기 시제품) 속성을 활용한 모듈, 객체, 메서드에 대한 이해이다. 자바스크립트에서는 함수 또한 객체다. 이는 함수도 속성을 가질 수 있다는 의미이며, 자바스크립트에서 생성자(사용자 정의의 객체생성(factory) 함수, 자바에서는 클래스를 이른바 설계도로 비유하는데 이 생성자는 초기 설계도면, 즉 레고의 default 조립도이다)에 의해 만들어진 모든 인스턴스는 속성과 메서드의 공유 저장소(default 조립도) 즉, 생성자의 프로토타입 속성에 접근할 수 있다(아키노, 2017)
콜백 함수(forEach)를 위한 this는 객체가 자동으로 할당되지 않으므로, 수동으로 명시할 수 있어야 하는데 함수의 bind라는 메서드를 사용하여 어떤 객체가 소유자가 되어야 하는지 지정해야 한다. bind는 유닉스의 소켓통신에서 지정되지 않은 포트(Unassigned port)나 할당된 포트(Well-known port)와 URL을 함께 묶어('binding') TCP 통신 접속을 할 때 칭하는 용어이기도 하다. 어쨌든 자바스크립트에서 함수는 실제 객체이고 자체 속성과 bind 같은 메서드를 가질 수 있다는 사실을 기억한다(아키노, 2017).
bind 메서드는 객체 인자를 전달받고 새로운 버전의 함수를 반환한다. 새 버전의 함수를 호출하면 이는 bind로 전달된 객체인자(인스턴스 참조자, 파라미터)를 함수 내에서 this의 값으로 사용할 것이다.
forEach 콜백은 소유자가 없기 때문에 콜백 내의 this는 undefined이다. bind를 호출하고 Cafe 인스턴스를 참조자로 전달하여 수정해보자. cafe.js에 bind 호출을 아래와 같이 추가한다.
이 개념을 객체 지향 언어에서 메시지 전달(Message Passing)이라고 일컫는다.
참조
크리스 아키노. (2017). FRONT-END WEB DEVELOPMENT: The big NERD ranch guide. (2016). 한국 번역판 역자 이지은(2017). 제대로 배우는 프런트엔드 웹 개발. 서울 : BJ(비제이 퍼블릭).