https://programmers.co.kr/learn/courses/30/lessons/72411
여러명의 손님이 시킨 메뉴조합중 조합 개수별로 인기가 제일 높은 조합을 고르는 문제다.
입력: [orders, course]
- orders: 2 이상 20이하의 배열길이
- 각 원소: 길이가 2 이상 10이하인 문자열
- 각 문자열은 대문자로만 이뤄져있음
- 각 문자열은 같은 알파벳이 중복되자 않음
- course: 1 이상 10 이하의 배열길이
- 각 원소: 길이가 2이상 10이하인 자연수가 오름차순 정렬돼있음
- 각 원소는 같은값이 중복되어 있지 않음
출력: 조합 개수별로 인기가 제일 높은 조합의 배열목록을 출력함
- 배열에 저장된 알파벳들은 오름차순으로 정렬되어있음.
- 주문횟수가 같다면 같은 조합 모두 배열에 저장함
- orders, course는 무조건 return하는 배열 길이가 1이상이 되도록 주어짐.
정답을 구하는 과정은 간단하다.
// 조합을 구하는 함수
function getCombination(input, end, start=0, result=[], tmp=[]) {
if (tmp.length === end) {
result.push(tmp);
return;
}
for (let i=start; i<input.length; i++) {
getCombination(input, end, i+1, result, [...tmp, input[i]]);
}
return result;
}
function solution(orders, course) {
const resultCourse = {};
const maxCntCombis = {};
let result = [];
// orders의 모든 조합을 계산함
orders.forEach((order) => {
// 매개변수로 넘어온 order문자열을 배열로 변환
const orderArr = order.split("").sort();
// 모든 course 순환
course.forEach( (courseNum) => {
// order배열의 course개 조합
// 문자열로 치환하고 1차원 배열로 바꿔줌
const combis = getCombination(orderArr, courseNum)
.map( combi => combi.join(""));
// reeulstCourse 객체에 해당 메뉴 조합을 주문한 횟수를 저장함
combis.forEach( combi => {
resultCourse[combi] = (resultCourse[combi] || 0) + 1;
})
});
});
// 계산한 조합에서 주문수가 가장 높은 조합만 저장함
Object.entries(resultCourse).forEach( (v) => {
const menuLength = v[0].length;
const nowCombi = maxCntCombis[menuLength];
const combi = v[0];
const cnt = v[1];
// 손님들이 두번 이상 주문한 메뉴라면
if (cnt >= 2) {
// 객체에 현재 조합이 있는경우
if (nowCombi){
// 객체에 저장된 조합보다 현재 조합의 주문횟수가 더 많은경우
if (cnt > nowCombi.cnt) {
maxCntCombis[menuLength] = {
cnt,
combis: [combi]
}
// 겍체에 저장된 조합과 현재 조합의 주문횟수가 같은경우
}else if (cnt === nowCombi.cnt) {
maxCntCombis[menuLength].combis.push(combi);
}
}
// 객체에 현재 조합이 없는경우
else {
maxCntCombis[menuLength] = {
cnt,
combis: [combi]
}
}
}
});
// 결과를 result에 저장함
Object.entries(maxCntCombis).forEach ( (v) => {
const combis = v[1].combis;
combis.forEach ( (combi) => {
result.push(combi);
});
});
return result.sort();
}
const orders = ["ABCDE", "AB", "CD", "ADE", "XYZ", "XYZ", "ACD"]
const course = [2,3,5];
const a = solution(orders, course);
console.log(a);