일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | 5 | ||
6 | 7 | 8 | 9 | 10 | 11 | 12 |
13 | 14 | 15 | 16 | 17 | 18 | 19 |
20 | 21 | 22 | 23 | 24 | 25 | 26 |
27 | 28 | 29 | 30 |
- 리액트
- 네트워크
- 타입스크립트
- typescript
- Algorithm
- html
- 해시
- react-query
- BFS
- 알고리즘
- 프로세스
- CS
- #프로젝트캠프 #프로젝트캠프후기 #유데미 #스나이퍼팩토리 #웅진씽크빅 #인사이드아웃 #IT개발캠프 #개발자부트캠프 #리액트 #react #부트캠프 #리액트캠프
- React.js
- 메모리
- ip
- 개발자부트캠프
- 프로그래머스
- 스나이퍼팩토리
- javascript
- 인사이드아웃
- IT개발캠프
- 웅진씽크빅
- cs #네트워크
- 유데미
- react
- App Runner
- 스레드
- 프로젝트캠프
- 자바스크립트
- Today
- Total
Bin's Blog
[프로그래머스] Level2 - 우박수열 정적분(Javascript) 본문
프로그래머스
코드 중심의 개발자 채용. 스택 기반의 포지션 매칭. 프로그래머스의 개발자 맞춤형 프로필을 등록하고, 나와 기술 궁합이 잘 맞는 기업들을 매칭 받으세요.
programmers.co.kr
📝문제 요약
1️⃣ 콜라츠 추측을 이용해서 자연수 k가 1이 될 때까지 다음 작업을 반복한다.(짝수는 2로 나누고, 홀수면 3으로 나누고 1을 더한다, 나온 수가 1보다 크면 계속 과정을 반복한다)
2️⃣ 초항이 k인 우박수열의 꺾은선 그래프를 정적분한다.
3️⃣ 어떤 범위에 대한 정적분의 결과를 구해야 한다.
4️⃣ 주어진 구간의 시작점이 끝점보다 크면 결과는 -1, 같으면 결과 0을 반환한다.
📚중요 포인트
1️⃣ 나는 크게 3가지 함수를 구현해서 문제를 해결하고자 했다. 우박 수열을 구하는 함수, 구간의 넓이를 구하는 함수, 정적분의 결과를 생성하는 함수이다.
2️⃣ 우박 수열을 구하는 함수는 초항이 1이 되는 과정대로 함수를 구현했다. 구간의 넓이를 구하는 함수의 경우에는 현재 구간과 다음 구간의 면적을 구했는데, 이 때 사다리꼴 공식을 활용해서 해결했다.
3️⃣ 마지막으로 정적분 결과는 정적분의 구하는 구간들의 목록 [a, b]에서 a와 초항에서 1이되는 횟수를 b에 더한 값을 비교해서 시작 구간이 더 크면 -1 같으면 0을 return하고 아닌 경우에는 구간에 해당하는 값들을 reduce 메서드를 활용해서 합산해주었다.
✅ 성공 코드
// 우박수열
function collatz_sequence(n) {
//초항을 넣어주고 시작한다
let start = 0;
let sequence = [[start, n]];
// k가 1이 될 때까지
while (n > 1) {
// 만약 짝수면 2로 나누고
if (n % 2 == 0) {
n /= 2;
// 홀수면 3을 곱하고 1을 더한다.
} else {
n = (n * 3) + 1;
}
// [x좌표와, 계산된 y좌표]
sequence.push([++start, n]);
}
// 최종적으로 배열을 업데이트한다.
return sequence;
}
// 구간 넓이
function calculateCollatzAreas(number) {
let section = collatz_sequence(number);
let areas = [];
for (let i = 0; i < section.length-1; i++) {
// 지금 지점과 다음 지점의 숫자를 destructuring 방식으로 꺼낸다.
let [a, b] = section[i], [c, d] = section[i+1];
// 지금 지점과 다음 지점 구간의 면적을 구한다(사다리꼴 공식 활용)
areas.push((b + d) / 2);
}
return areas;
}
// 정적분의 결과 목록 구하기
function solution(k, ranges) {
let answer = [];
let area = calculateCollatzAreas(k);
// 초항을 1로 만드는데 걸리는 횟수
let number = area.length;
// 정적분 결과 구하기
ranges.map((element) => {
let [a, b] = element;
// 시작 지점이 끝지점보다 작으면 해당 구간의 정적분을 구한다.
if (a < number + b) {
return answer.push(area.slice(a, number + b).reduce((acc, cur) => acc + cur, 0))
// 시작지점과 끝지점이 같으면 면적은 0이다.
} else if (a == number + b) {
return answer.push(0);
// 시작지점이 끝지점 보다 크면 면적은 -1이다.
} else if (a > number + b ) {
return answer.push(-1);
}
})
return answer
}
📔느낀점
👉 다른 사람 풀이들을 보면 내 코드보다 하나의 함수 안에서 더 짧게 잘 작성한 코드들도 있다. 나는 이렇게 각 역할을 하는 함수들을 모듈화해서 기능 단위로 쪼개서 작성했다. 모듈화 하는 작업의 연습이 필요해서 문제 풀 때 적극적으로 시도해보고 있다.
👉 매번 알고리즘 풀면서 느끼지만 메서드를 적재적소에 활용하는 중요하다고 생각한다. 이번 문제 풀 때 어떤 메서드를 사용해야 할지 고민하면서 작성했다.
'Algorithm' 카테고리의 다른 글
[프로그래머스] Level2 - 과제 진행하기(Javascript) (0) | 2023.11.15 |
---|---|
[프로그래머스] Level2 - 두 원 사이의 정수 쌍(Javascript) (0) | 2023.11.07 |
[프로그래머스] Level2 - 디펜스 게임(Javascript) (0) | 2023.11.02 |
[프로그래머스] Level2 - 리코쳇 로봇(Javascript) (0) | 2023.10.30 |
[프로그래머스] Level3 - 베스트앨범(Javascript) (0) | 2023.09.14 |