[항해99 / 2주차] 🚢 23-04-10 ~ 23-04-16 WIL
한 주 돌아보기
이번주에 해낸 것 | 이번주에 하지 못한 것 |
😎 안돼도 그냥 하기 | 🤔 코어자바스크립트 완독하기 |
😎 알고리즘 테스트 통과하기 |
✅ 안 돼도 그냥 하기
지난주에 썼던 WIL. 이번 주에 얼마나 지켰나? 보면 칼같이 50%를 달성했다. 코어 자바스크립트는 반 읽었고 바닐라JS로 계산기 만들기도 1/2 만큼을 남겨두고 있고 과제물도 한 개 제출했다. 이번주차도 내용이 어려워서인지 집중이 잘 안 됐는데 어떻게든 그냥 하려고 많이 노력했다. 스코프가 좀 크기도 했지만 눈 딱 감고 했으면 다 해낼 수 있었을 것 같아 아쉽지만 생각을 줄이고 그냥 하는 연습을 많이 할 수 있었다.
한동안 알고리즘이 안풀린다고도 이전에 썼었는데 안 풀리던 알고리즘이 아주 느린 속도로 다시 풀리고 있다. 알고리즘도 풀어보고 안되면 다음날 또 보고 그래도 안되면 또 보기를 정말 오래 했는데 내가 문제 풀이를 좀 어렵게 생각하고 있었다는 걸 알았다. 기술매니저님이 추천해 주신 책도 샀고... 시간을 더 잘 운용할 수 있다면 리액트주차를 병행하며 알고리즘 관련 개념도 조금 정리하고 싶다.
[이번 주에 공부하고 기록한 내용들]
- [프로그래머스 / JavaScript] Lv.1 행렬의 덧셈
- [프로그래머스 / JavaScript] Lv.1 로또의 최고 순위와 최저 순위
- [프로그래머스 / JavaScript] Lv.1 신규 아이디 추천 (ft. 테스트 케이스)
- [프로그래머스 / JavaScript] Lv.1 k의 개수
- [프로그래머스 / JavaScript] Lv.0 한 번만 등장한 문자
- [JavaScript] 브라우저 렌더링 과정(원리)
- [항해99 / TIL] 🚢 23-04-15 chatGPT에게 리액트 기초 물어보기
- [JavaScript] 자바스크립트로 동적 테이블 만들기 (ft. 버튼 클릭)
✅ 알고리즘 테스트 통과하기
목요일엔 알고리즘 테스트가 있었다. 알고리즘과 자료구조 공부라기보단 자바스크립트를 공부하고 이를 적용한 문제를 풀어보는 이런 난이도로 출제된 것 같았다.
처음 알고리즘을 풀 때는 이걸 내가 코드로 구현할 수 있다고?라는 마음이 들었지만 이젠 조금 익숙해져서 일단 해보자는 생각이 먼저 든다. 테스트를 풀 때도 이 문제에 완벽한 답을 한 번에 찾아내겠다고 생각하기보다는 일단 되는대로 먼저 풀어보고, 그 뒤에 다시 생각해 보자는 마음으로 접근하고 있다.
알고리즘 테스트는 아래와 같았다.
1.
[문제]
르탄이가 1000원을 가지고 편의점에서 물건을 사려고 한다. 편의점에는 500원, 100원, 50원, 10원이 충분히 있고, 편의점 직원은 언제나 거스름돈 개수가 가장 적게 잔돈을 준다. 르탄이가 편의점에서 물건을 사고 1000원 지폐 한 장을 냈을 때, 받을 잔돈의 개수를 구하는 프로그램을 작성하여라. (단, 물건의 가격은 10원 이상 1000원 미만이며, 1원 단위는 고려하지 않는다.)
[입출력 예]
check-in | result |
900 | 1 |
550 | 5 |
320 | 6 |
[지정 입력값]
check-in | result |
160 | 8 |
어떻게 나눠볼까 고민하다가, 일단 if문으로 답을 뽑아내는 과정을 쭉 적어보았다.
function solution(num){
let change = 1000 - num;
let answer = 0;
// ! if문을 이용한 풀이
if(change / 500 >= 1) {
answer += Math.floor(change / 500);
change = change - (500 * Math.floor(change / 500));
}
if(change / 100 >= 1) {
answer += Math.floor(change / 100);
change = change - (100 * Math.floor(change / 100));
}
if(change / 50 >= 1) {
answer += Math.floor(change / 50);
change = change - (50 * Math.floor(change / 50));
}
answer += Math.floor(change / 10);
change = change - (10 * Math.floor(change / 10));
console.log(answer);
}
let num = 160;
console.log(solution(num));
적고보니 answer에 값을 더하는 것과 잔돈 값을 구하는 표현식이 공통적으로 나타났다. 이걸 어떻게 해야 간결하게 뽑아낼 수 있을까?를 고민한 뒤 최종적으로 아래와 같이 코드를 작성해 제출했다.
function solution(num){
const money = [500, 100, 50, 10];
let change = 1000 - num;
let answer = 0;
for(let coin of money) {
if(change >= coin) {
answer += Math.floor(change / coin);
change = change - (coin * Math.floor(change / coin));
}
}
return answer;
}
const num = 160;
console.log(solution(num));
거스름돈이 거슬러받을 동전보다 큰지 아닌지를 판별해 액수가 큰 동전부터 차례대로 계산할 수 있도록 for문을 작성했고, 배열이므로 for...of를 이용했다. if문만 사용할 때보다 훨씬 간결하고 코드를 읽기도 편하다.
2.
[문제]
"OOXXOXXOOO"와 같은 OX문의 결과가 있다. O는 문제를 맞은 것이고, X는 문제를 틀린 것이다. 문제를 맞은 경우 그 문제의 점수는 그 문제까지 연속된 O의 개수가 된다. 예를 들어, 10번 문제의 점수는 3이 된다.
"OOXXOXXOOO"의 점수는 1+2+0+0+1+0+0+1+2+3 = 10점이다.
OX퀴즈의 결과가 주어졌을 때, 점수를 구하는 프로그램을 작성하시오.
(단, OX문의 결과는 0보다 크고 80보다 작은 문자열이 주어진다. 또한 문자열은 O와 X만으로 이루어져 있다.)
[입출력 예]
check-in | result |
OOXXOXXOOO | 10 |
OXOXOXOXOXOXOX | 7 |
OOOOOOOOOO | 55 |
[지정 입력값]
check-in | result |
OXOOOXXXOXOOXOOOOOXO | 27 |
이 문제도 어떤 함수를 써야겠다는게 단박에 떠오르지 않아 일단 할 수 있는 방법으로 답을 도출했다.
function solution(str){
let arr = str.split('X').filter(x => x != '');
let answer = 0;
for(let i = 0; i < arr.length; i++) {
for(let j = 1; j <= arr[i].length; j++) {
answer += j;
}
}
console.log(answer);
}
let str = 'OXOOOXXXOXOOXOOOOOXO';
console.log(solution(str));
O일 때만 값을 더해야 하므로 split으로 X를 모두 빼고, X인 값은 ''로 출력되므로 filter를 이용해 ''값을 제거했다. 최종적으로 ['O', 'OOO', 'O', 'OO', ...] 처럼 X 사이들의 O들만 배열에 담길 수 있도록 만들었다. 그 후 중첩 for문을 돌려 해당 인덱스에 O가 몇 개 있는지를 순차적으로 더했다.
하지만 for문을 두 번 돌린다면 입력값이 아주 커졌을 때 시간이 오래 걸릴 것이고, 내부에 O가 N개 있다면 1 + 2 + 3 + ... + N을 여러 번 반복해야 하는 상황이라 1번 문제처럼 이것 또한 공통적으로 뽑아낼 수 있는 방법이 없을지 고민했다.
그러다 문득 프로그래머스 덧셈 문제를 풀면서 '아 학교 다닐 때 이런 공식도 배웠었지?!' 하고 무릎을 쳤던 가우스 덧셈공식이 떠올랐다. 정말 오래된 기억 속에 있던 그 공식을 코드로 구현해 쉽게 덧셈문제를 풀어낸 것을 보며 신박하기도 했고 나중에도 잘 쓸 수 있겠다 싶어 코드를 아예 외워버렸었는데, 그 공식을 여기에 쓰면 되겠다 생각했다.
[가우스 덧셈공식]
1부터 연속되는 끝수 N까지의 합일 때,
(1 + N) * (Math.abs(1 - N) + 1) / 2
function solution(str){
const arr = str.split('X').filter(x => x != '');
let answer = 0;
arr.forEach(o => answer += o.length * (o.length + 1) / 2);
return answer;
}
let str = 'OXOOOXXXOXOOXOOOOOXO';
console.log(solution(str));
O만 있는 배열은 동일하게 뽑아내고, 배열 값을 순회하며 해당 인덱스의 length만큼 가우스 덧셈공식을 적용해 answer값에 담았다.
알고리즘 테스트는 1번(1점), 2번(2점), 3번(3점)이 있었고 3점이 통과 점수였다. 시험을 마치고 다음날 스터디 준비를 빨리 해야 했기 때문에 간단한 1, 2번을 최대한 빨리 풀고 3번은 풀지 않은 채 시험을 마쳤다. 다른 분들을 보니 시간이 오래 걸려도 3번을 풀고 나오신 분들이 많았어서 그래도 시험인데 한 번 풀어볼걸 그랬나 싶어 반성했다. 나중에 풀어보려고 문제는 따로 적어뒀으니 다음주 WIL 작성하기 전에 한 번 풀어보자.
이전 WIL에도 적었었지만 알고리즘 문제를 푼다는게 개발을 어느 정도 잘하는 사람들이 하는 것이라는 편견이 있었고 (LV.0, 1의 존재를 아예 몰랐다) 내가 풀 수 있을까? 라는 생각을 가지고 시작했었다. 그런데 어떻게 하면 더 효율적으로 풀 수 있을지 차근차근 생각하는 내 자신을 보며 조금 성장했구나를 테스트를 풀며 많이 느꼈다. 항해 시작 전 한라산 등산을 할 때 너무 힘들어서 반걸음, 반걸음씩 천천히 걷던 게 모여 결국 정상에 도착했을 때가 생각나기도 했다. 앞으로도 이렇게 조금씩 꾸준히 성장해 가길!
❌ 코어 자바스크립트 완독하기
항해 본과정 1주차를 시작하자마자 별안간 코어 자바스크립트를 배우길래 온보딩을 뒤늦게 시작해서 혼공자스도 못 받았던 나는.. 왜 이렇게 난이도가 높지? 하고 혼란스러웠다. WIL은 일요일에 쓰지만 주차별 새로운 발제는 금요일에 진행되어서 지금 리액트를 막 시작했는데 리액트 공부를 시작하니 왜 항해에서 코어 자바스크립트 공부를 시켰는지 어렴풋이 느껴졌다. 불변성을 지켜주기 위한 복사 방법, 리액트에서도 자주 쓰이는 ES6문법, 클로저를 기반으로 한 훅.. '왜' 해야 하는지에 대해서 더 빨리 알았다면 더 이 악물고 공부했을 텐데 이걸 자바스크립트 주차가 끝난 뒤에 셀프로 깨달아서 아쉽다. 이걸 왜 해야 하는지 목적과 선택에 따른 근거가 있어야 재미를 붙이는 성향이라 '왜'를 깨달은 금요일부터 뒤늦게 코어 자바스크립트를 깊게 다시 읽었다. 목표는 완독이었지만 이해한 파트를 기준으로 반 밖에 못 읽어서 아쉽다.
이번 주 이것저것
사소한 것
게더에서 알림이 울려서 들어가보면 저렇게 불러주신 분 캐릭터 사진이 같이 뜰 때가 있다. 심오한 닭 분장을 하고 맑은 알림 소리로 부르는 게 너무 웃겨서 볼 때마다 웃는다. 즐겁다.
깃허브에 잔디를 심는 이벤트가 있었고 R반 세 명 중 한 명에 당첨되었다! 뿌듯하다. 모내기왕 상품으로 햇반이랑 미소된장이 오는 중이다. 귀엽다.
지금까지 했던 개발 공부 방법 중 화면 공유 모각코가 제일 효과적이었다. 화면이 실시간으로 보여지니 다른 방해 없이 정말 공부에만 집중할 수 있다. 다른 분들과 함께 공부하고 싶어 스터디를 만들었고 매니저님도 별도 공간을 따로 만들어주셔서 감사한 마음으로 참여하고 있다! 역시 화면공유 모각코는 공부가 정말 정말 잘된다👍🏼
이번 주에 시니어 코치님과의 첫 그룹 면담이 있었다. 자기 소개를 해야 해서 어떤 일을 했고 왜 프론트엔드 개발자가 되려 하는지, 앞으로 어떻게 하고 싶은지 말씀드렸다. 코치님이 예전의 본인 모습을 보는 것 같다고 말씀해 주셨다. 어려운 걸 쉽게 설명하는 게 진짜 어렵고 멋있다고 생각해서 (내 꿈은 멋있는 사람) 리액트 강의를 들으며 코치님이 멋있다고 생각하고 있었는데 멋있는 분이 좋은 말씀을 해주시니 아주 강력한 동기부여가 되었다. 어려워도 중꺾마!
알게된 것
알고리즘 문제를 푼 이후로 생략할 수 있는 괄호는 생략해서 한 줄에 코드를 작성할 때가 있는데 위의 내가 작성한 코드를 보니 위쪽 if-else는 한 줄씩으로 처리하고 아래의 if-else는 중괄호를 사용해서 뭔가 통일성이 없어 보였다. 기술 매니저님께 해당 코드를 보여드리고 코드 통일성이 없어 보이는지, 어떻게 작성하는 게 좋은지 여쭤보았다. 위쪽의 if-else같은 경우는 한눈에 파악이 어려울 수 있으니 중괄호를 사용하는 것을 권장해 주셨고, 협업을 할 때는 중괄호 생략 또한 팀끼리 미리 규칙을 정해두고 작업한다고 한다는 것을 새로 알게 되었다!