회원가입을 하면 원하는 문장을
저장할 수 있어요!
다음
AWS 이용 중이라면 최대 700만 원 지원받으세요
우리는 왜 알고리즘을 공부할까요? 기초 소양을 쌓기 위해서? 좀 더 나은 개발자가 되기 위해서? 아주 틀린 이야기는 아니지만, 좀 더 솔직하게 얘기해 보겠습니다. 아마 대부분은 코딩 테스트를 통과하기 위해 알고리즘을 공부하고 있을 겁니다.
회원가입을 하면 원하는 문장을
저장할 수 있어요!
다음
회원가입을 하면
성장에 도움이 되는 콘텐츠를
스크랩할 수 있어요!
확인
우리는 왜 알고리즘을 공부할까요? 기초 소양을 쌓기 위해서? 좀 더 나은 개발자가 되기 위해서? 아주 틀린 이야기는 아니지만, 좀 더 솔직하게 얘기해 보겠습니다. 아마 대부분은 코딩 테스트를 통과하기 위해 알고리즘을 공부하고 있을 겁니다.
요즘은 취업과 이직은 물론이고, 부트캠프나 대외 활동에서도 지원자를 가려내기 위해서 코딩 테스트를 요구하는 시대입니다. 물론 최근에는 온라인 저지(Online Judge)로 진행하는 코딩 테스트 대신, 실무형 과제를 제출하는 곳도 많이 있는 것 같습니다. 하지만 알고리즘 코딩 테스트는 여전히 많은 기업에서 실재(實在)합니다.
지금으로부터 약 1년 전, 저 역시 복학을 앞둔 상황에서 처음 알고리즘 공부를 시작했습니다. 공부 목적은 당연하게도 코딩 테스트를 준비하기 위해서였습니다. 알고리즘 공부를 본격적으로 해본 건 처음이었기에 처음에는 실력도 부족했고 두려움이 컸습니다. 사실 은연중에 ‘알고리즘 공부가 굳이 필요한가?’라는 생각도 있었기에, 주변 사람들에게 이를 확인받고 싶어 물어보기도 했습니다.
“프론트엔드 개발자에게도 알고리즘 공부가 중요할까요?”
특히 취업을 준비하고 있거나 또는 개발자로 커리어 전환을 시도하는 분이라면 이런 불안감이 더욱 커지는 것 같습니다. 저도 그랬거든요. ‘프론트엔드 개발자라면 일단 서비스부터 잘 만들어야 할 것 같은데, 알고리즘은 또 언제 배우냐?’라며 막막한 마음이 들었던 것이 사실입니다. 실무에서 써먹을 일도 별로 없을뿐더러, 무엇보다 재미가 없습니다. 하지만 코딩 테스트 때문에 울며 겨자 먹기로 하는 수밖에 없었습니다.
저도 이런 고민을 했던 입장으로써, 오늘은 프론트엔드 개발자의 관점에서 알고리즘 공부의 중요성에 대해 솔직하게 이야기해보고자 합니다. 이번 포스트를 통해 프론트엔드와 알고리즘 공부 사이에서 고민하는 독자들에게 도움이 되었으면 좋겠습니다.
TL;DR
|
우선 글을 시작하기 전에, 제가 알고리즘과 관련해서 여러분께 조언을 드릴 입장인지는 모르겠다는 생각이 들어서 조심스럽습니다. 제가 백준(프로그래밍 문제를 풀고 온라인으로 채점 받을 수 있는 곳) 외에 다른 플랫폼은 안 써봐서 모르겠는데 대충 골드 1 정도까지 공부했습니다.
골드 1은 노베이스에서 6개월 동안 매일 한두 시간씩 꾸준히 문제를 풀다 보면 어렵지 않게(?) 달성할 수 있는 수준입니다. 이 정도면 골드 4, 5 난이도 문제를 30분 내외로 풀 수 있을 정도이며, 일반적인 기업에서 커트라인으로 제시하는 코딩 테스트는 무난히 통과할 수 있는 것 같습니다. 덕분에 작년에 네이버와 카카오(1차) 코딩 테스트를 통과한 경험이 있습니다.
지금부터는 제 경험을 바탕으로 프론트엔드 개발자가 알고리즘 공부를 바라봐야 할 관점을 일문일답으로 요약하고자 합니다. 아래에서 이야기할 코딩 테스트는, 전형적인 개발자 채용 과정에서 진행되는 알고리즘 유형과 난이도를 기준으로 한다는 것을 말씀드립니다.
“그렇습니다.”
우선 프론트엔드라는 단어를 떼어놓고 생각해봅시다. 개발자에게 알고리즘은 어떤 의미일까요? 당연히 떼려야 뗄 수 없는 관계입니다. 알고리즘은 곧 문제 상황이 주어졌을 때 제한된 시간과 메모리 내에서 가장 효율적으로 문제를 해결할 수 있는 방법입니다.
문제를 해결하는 방법은 여러 가지가 있을 수 있지만, 모든 방법이 유용한 것은 아닙니다. 문제를 해결할 수는 있지만 정답을 얻어내기까지의 과정이 굉장히 오래 걸린다면, 이를 이용해 현실 세계에서의 문제를 풀기는 어려울 것입니다. 우리에게 주어진 시간과 자원, 그리고 인내심(…)은 유한하기 때문입니다.
따라서 똑같은 문제 상황이라고 해도 최소한의 시간, 최소한의 공간을 사용하는 알고리즘이 더 유용합니다. 또한 목적에 맞는 자료구조를 활용하면 알고리즘의 효율성을 더욱 개선할 수 있습니다. 이 덕분에 컴퓨터 이론은 과학(Science)에서 벗어나 보다 공학적(Engineering)인 가치를 갖게 됩니다.
“항상 그런 것 같지는 않습니다.”
하지만 프론트엔드라는 단어를 붙이면 좀 애매해집니다. 대우(contraposition)로 생각해보면, 질문이 ‘알고리즘을 배우지 않으면 프론트엔드 개발자가 될 수 없는가?’가 됩니다. 제 경험상 이 전제는 ‘항상 옳지는 않다’라는 생각이 들었습니다. 왜냐하면 그 반례를 많이 봤고, 저 역시 그 반례 중 하나였기 때문입니다.
HTML과 CSS는 외울 게 많긴 하지만, 사용 방법만 알면 되지 내부 알고리즘까지 우리가 알 필요는 없습니다. ‘자바스크립트(JavaScript)’에서 일부 로직에 알고리즘을 적용해 최적화할 수 있지만, 정렬이나 탐색 등 웬만한 기본적인 알고리즘은 이미 API가 제공됩니다. 없다면 라이브러리나 프레임워크를 쓰면 되죠. 생각보다 Node.js 생태계는 무척 잘 되어 있습니다. 즉 우리는 알고리즘 구현 자체를 알기보다는 제공되는 기능을 적재적소에 잘 써먹기만 하면 대부분의 문제를 해결할 수 있습니다.
저도 3년간 알고리즘 기초에 대한 빠삭한 이해 없이 업무를 진행했지만, 업무 중 알고리즘을 몰라서 개발에 문제가 생긴 경우는 거의 없었습니다. 오히려 성능보다는 가독성을 중요시하는 코드를 더 많이 짰습니다. 물론 재귀 함수로 트리 구조의 레이아웃을 구현하거나 계산 결과를 ‘메모이제이션(동일한 계산을 반복해야 할 경우 한 번 계산한 결과를 메모리에 정해 두었다가 꺼내서 중복 계산을 방지하는 것)’하는 것처럼 비즈니스 로직 단계에서 최적화를 진행하면 좋은 경우도 있긴 합니다.
주변에 있는 여러 개발자분의 의견도 비슷합니다. 대부분 프론트엔드 개발자도 ‘알아두면 좋긴 한데, 다른 직군에 비해 알고리즘이 크게 중요한 것은 아니다’라는 이야기를 해주셨습니다. 애초에 직군과 상관없이 실무에서 알고리즘을 쓸 일이 별로 없다는 생각도 많이 들었고요.
“크게 네 가지 이유가 있는 것 같습니다.”
그렇다면 왜 일반적으로 프론트엔드에서 알고리즘이 중요하지 않다고 생각할까요? 제가 생각했을 때 네 가지 이유가 있는 것 같습니다.
우선 알고리즘 최적화가 필요한 문제 상황 자체가 별로 없기 때문입니다. 프론트엔드의 주요 역할은 HTML과 CSS를 이용한 퍼블리싱, 데이터 기반의 상호작용 가능한 UI 구현, 그리고 백엔드와의 HTTP 통신 정도가 생각이 나는데요. 이 작업들은 알고리즘에 대한 깊은 지식 없이도 구현이 가능합니다. 즉, 프론트엔드 자체에서 매우 복잡한 로직을 수행하는 것이 아니라면 알고리즘까지 이용해가면서 문제를 최적화해야 할 상황 자체가 자주 발생하지 않습니다. 오히려 유지보수를 위해 최적화를 포기하고 코드의 가독성이나 재사용성을 높이는 경우가 더 많습니다.
만약 복잡한 로직이 필요하다고 해도 웹은 서버-클라이언트 구조를 따르므로 대부분의 복잡한 비즈니스 로직은 서버에 탑재됩니다. 서버(백엔드)는 다량의 데이터를 안전하게 보관하고 내부 동작 방식을 숨길 뿐만 아니라 여러 요청을 동시에 처리하는 데 최적화되어 있습니다. 따라서 클라이언트(브라우저)는 서버에게 필요한 기능을 요청하고 그 결과를 받기만 하는 구조가 바람직합니다.
위의 이유로 브라우저에서는 대용량의 데이터를 처리하는 경우가 잘 없습니다. 애초에 브라우저 자체가 대용량 데이터의 처리를 위해 만들어진 것이 아닙니다. 브라우저의 역할은 사용자를 대신해 백엔드와 상호작용할 수 있는 프론트엔드 인터페이스를 실행시켜주는 것입니다. 알고리즘의 효율성은 데이터 규모(NN)가 커질수록 극적인 효과를 내는데, 브라우저의 성능이 제한적이기 때문에 알고리즘을 이용해 최적화할 수 있는 기댓값이 상대적으로 크지 않습니다.
만약 알고리즘적인 접근이 필요한 경우가 있다고 해도 브라우저나 라이브러리, 프레임워크 등에서 이를 추상화한 API를 이미 제공하며, 이것을 쓰는 것이 효율적이기 때문입니다. ‘추상화되었다’는 말은 우리가 내부 구조를 모르고도 사용할 수 있는 것을 의미합니다. 우리는 getElementById
함수가 DOM 트리 구조를 DFS로 탐색한다는 것을 알지 못해도 됩니다. 해당 API가 입력으로 ID 속성을 받고, 출력으로 DOM 엘리먼트가 반환된다는 사실 자체만 이해하고 쓰는 게 더 경제적입니다.
요약하자면, 우리가 프론트엔드에서 일상적으로 풀어야 할 문제들은 이미 추상화된 형태로 제공되는 알고리즘들의 조합으로 해결 가능하며 이것이 효율적이기 때문입니다. 따라서 추상화된 형태로 제공되는 알고리즘의 입출력만 잘 알면 실무에 있어서는 큰 지장이 없기 때문에 이런 일이 가능한 것 같습니다.
“단순히 주어진 요구사항 구현뿐만 아니라 성능과 효율성까지 챙기는 개발자가 되기 위해서는 배워야 합니다.”
오늘의 핵심을 꿰뚫는 질문입니다. 개인적인 생각으로는 알고리즘을 몰라도 프론트엔드 개발이 가능하긴 하지만, 더 넓은 시야를 가진 개발자로 성장하기 위해서는 알고리즘 공부가 필요하다고 생각합니다. 생각의 규모를 조금 더 확장해 생각해본다면, 우리가 왜 CS를 공부해야 하는지에 대한 답과도 일맥상통합니다.
그렇게 생각하는 첫 번째 이유는 알고리즘과 자료구조의 조합을 이해하고 있으면 우리가 실제로 해결하고자 하는 문제 상황에 최적화된 구조를 쉽게 떠올리고 설계할 수 있기 때문입니다. 흔히 이야기하는 ‘컴퓨팅적 사고(Computational Thinking)’가 바로 이것입니다.
Array.find()
를 사용할 수도 있지만, 그 값이 정렬되어 있다면 이분 탐색으로 값을 찾는 것이 훨씬 더 빠릅니다.
이를 잘 이용한다면 소프트웨어 개발 시간을 줄이면서 성능과 효율성을 높일 수 있고, 수준이 매우 뛰어나다면 비즈니스적 성과로도 이어질 수 있습니다.
두 번째 이유는 환경이나 플랫폼의 변화에도 흔들리지 않는 개발자가 될 수 있기 때문입니다. 우리는 알고리즘이 추상화된 형태의 API 또는 라이브러리를 많이 쓰곤 합니다. 하지만 그것만 가지고 “알고리즘을 이해했다”라고 이야기할 수 있을까요? 정확하게 이야기하자면 우리는 다른 개발자들이 만들어 놓은 기반 위에서 동작하는 API를 그저 사용한 것뿐입니다.
이러한 개발자들은 특정 환경과 특정 플랫폼에 단단히 종속될 수 있다는 점에서 위험합니다. 원리를 이해한 것이 아니라 기능을 사용했기 때문입니다. 따라서 환경이 바뀌거나 본인이 익숙하지 않은 플랫폼에서는 적응에 상당한 어려움을 겪을 것입니다.
만약 여러분이 JavaScript Web API에서 기본으로 제공되는 getElementById
를 파이선(Python)에서 구현해야 하는 일을 맡게 됐다면? Python에서 기본 제공되는 자료구조인 힙, 우선순위 큐 등의 자료구조를 JavaScript에서 구현해야 하는 일을 맡게 된다면? 게다가 만약 내가 필요한 기능의 라이브러리를 사용할 수 없는 환경이라면?
언어 자체가 익숙하지 않다면 문법이 헷갈릴 수 있겠지만 이건 큰 문제가 아닙니다. 문법이야 배우면 되니까요. 알고리즘과 자료구조에 대한 이해만 있다면, 환경과 플랫폼에 상관없이 효율적인 문제 해결 방법을 제시할 수 있다는 사실이 더 가치 있는 것입니다.
마지막 이유는 모든 응용 기술들은 결국 기초 기술을 기반으로 만들어지기 때문입니다. 결국 하고 싶은 이야기는 ‘어느 정도 기초에 충실하자’라는 겁니다. 모든 개발자는 본인이 사용하고 있는 기술 그 자체에서 이해를 멈추는 것이 아니라, 그것을 떠받치고 있는 기술을 이해하기 위해 노력해야 할 필요가 있습니다. 그래야만 본인의 기술을 더 잘 활용할 수 있습니다.
비즈니스 로직이 어떻게 알고리즘과 자료구조로 추상화되며, 그렇게 작성한 React와 TypeScript 코드가 어떻게 JavaScript로 어떻게 컴파일되고, 이 JavaScript는 HTML, CSS와 함께 어떻게 브라우저에서 동작하는지, 그 브라우저는 어떻게 운영체제에서 관리되며, 운영체제는 어떻게 다양한 호스트에서의 네트워크 연결을 중재하는지도 생각해봐야 합니다.
이런 과정들이 불필요해 보이나요? 우리가 쉽게 사용하는 기술들은 공짜로 얻어진 것이 아닙니다. 기반이 되는 모든 기술을 이해하자는 것이 아닌, 최소한의 지식 정도는 알고 있자는 것입니다.
“기업 입장에서 수많은 지원자의 기본기를 검증할 수 있는 가장 경제적인 방법이기 때문입니다.”
위에서 뭔가 거창하게 이야기했지만, 사실 기업 입장에서 저렇게 사명감(?) 넘치는 취지로 알고리즘 코딩 테스트를 보는 것은 아니라고 생각합니다. 그 이유는 알고리즘 코딩 테스트가 기업 입장에서 매우 경제적인 평가 방법이기 때문입니다.
물론 기본기를 평가하는 목적도 있지만, 알고리즘 테스트를 도입하면 지원자들의 점수를 객관적으로 수치화할 수 있습니다. 덕분에 점수에 따라 지원자들을 일렬로 줄 세울 수도 있고, 무의미한 실력의 지원자를 쉽게 걸러낼 수도 있습니다. 또한 빠르면 한두 시간 내에 평가가 끝나기 때문에 내부 구성원들의 리뷰가 필요한 과제 전형에 비해 리소스를 덜 쓰기도 합니다. 특히 어느 정도 규모가 있는 회사일수록 지원자는 많은 반면 인원은 신중하게 뽑기 때문에, 면접 전까지는 점수로 커트하려는 목적도 있습니다.
알고리즘은 테스트 케이스 통과 여부에 따라 정답과 오답이 명확하게 드러나고, 효율성을 수치화하기에도 적합하기에 코딩 테스트의 평가 기준으로 사용되고 있는 듯합니다. 사실 기업 입장에서도 모든 지원자의 편의를 봐주고 코드를 읽어볼 수는 없는 노릇이니, 이해는 갑니다.
“맞습니다만, 문제 접근 방식을 평가하기 위한 목적도 있습니다.”
목적 자체가 다르긴 합니다. 단순히 일회성으로 정답을 찾기 위한 코드, 그리고 유지보수성과 재사용성을 고려하면서 작성한 코드는 분명 다릅니다.
그래서일까요? 최근에는 일부 기업에서 코딩 테스트 대신 과제나 포트폴리오를 더 많이 보는 전형도 생기고 있다고 합니다. 하지만 채용 과정을 진행하는 것은 전적으로 기업의 선택이기 때문에, 어떤 것이 정답이라고 이야기할 수는 없습니다. 구글에서는 아직 알고리즘으로 코딩 테스트를 본다고 합니다. 기업의 입장에서 변호하자면, 알고리즘 코딩 테스트를 통해 효율성뿐만 아니라 문제 접근 방식에 대한 평가도 진행할 수 있습니다.
면접에서 코딩 테스트 때 제출한 코드를 리뷰하는 경우도 꽤 있습니다. 또한 라이브 코딩 테스트 같은 경우에는 면접관이 일부러 요구사항이 모호한 문제를 주기도 합니다. 따라서 지원자는 요구사항을 명확히 하기 위한 질문을 면접관에게 해야 하고, 이렇게 커뮤니케이션하는 과정에서 문제 접근 방식을 평가할 수 있습니다.
만약 여러분이 가고 싶은 회사에서 알고리즘으로 코딩 테스트를 본다면? 뭐, 조금 냉정하게 들리겠지만, 포기하거나 공부해서 시도하거나 둘 중 하나밖에 없습니다. 사실 이게 불합리하다고 느껴진다면 과제로 검증하는 회사를 지원해야 합니다.
“본인이 필요하다고 느껴질 때 하면 됩니다.”
저처럼 각종 교육 과정이나 채용 전형으로 요구되기 때문에 미리 준비해둘 수도 있고, 그냥 본인이 더 나은 개발자가 되고 싶어서 공부할 수도 있습니다. 자투리 시간을 생산적으로 활용하고 싶을 때도 틈틈이 공부하기 좋습니다. (뭐 군대에 있을 때라던가…)
개인적으로는 완전 노베이스 기준 매일 1~2시간 공부 기준 6개월 정도 했을 때 웬만한 알고리즘 코딩 테스트는 통과했던 것 같습니다. 중요한 시험이나 면접이 있다면 이를 감안해서 미리 준비할 필요가 있을 겁니다.
“목표에 따라 다른 것 같지만 취업을 위해서라면 기본기만 챙기면 충분합니다.”
저는 아래 범위를 위주로 공부했습니다.
개인적으로 알고리즘은 설계를 쉽고 효율적으로 만들어주는 개발자의 기초 체력이라고 생각합니다. 물론 많이 알수록 좋지만 올림피아드에 나가지 않는 이상 알고리즘 그 자체에만 매달리는 것은 그리 효율적이지는 않다고 생각합니다. 기본이라는 기준이 대부분의 기업 코딩 테스트에서 요구하는 수준인 것 같고, 그 이후로는 본인이 전문성을 가져야 하는 직군의 공부를 더 하는 게 좋다고 생각합니다.
그렇기 때문에 만약 프론트엔드 개발자가 되고 싶긴 한데 프론트엔드 자체에 대한 지식이 부족하다면, 이 경우에는 알고리즘보다는 프론트엔드부터 공부하는 걸 추천합니다. 즉 프론트엔드 개발 생태계에 어느 정도 익숙해진 상태에서 알고리즘 공부를 병행하는 방식이 괜찮을 것 같습니다.
적다 보니 내용이 많이 길어졌습니다. 건조하게 ‘알고리즘 공부는 당연히 중요하다’라고 하기보다는 좀 더 실무적인 입장에서, 그리고 프론트엔드 개발자의 관점에서 글을 한 번 주절주절 써봤습니다. 사람에 따라 의견이 다를 수도 있는데, 건전한 피드백과 토론은 언제든 환영이니 댓글 남겨주시기를 바랍니다.
그리고 글을 마무리하기 전에 덧붙여봅니다. 프론트엔드라는 직군에 매몰되어 알고리즘을 비롯한 CS 공부 자체를 소홀히 하지는 맙시다. 프론트엔드 개발자이기 전에, 우리는 개발자니까요.