숫자나라 기사단의 각 기사에게는 1번부터 number까지 번호가 지정되어 있습니다. 기사들은 무기점에서 무기를 구매하려고 합니다.
각 기사는 자신의 기사 번호의 약수 개수에 해당하는 공격력을 가진 무기를 구매하려 합니다. 단, 이웃나라와의 협약에 의해 공격력의 제한수치를 정하고, 제한수치보다 큰 공격력을 가진 무기를 구매해야 하는 기사는 협약기관에서 정한 공격력을 가지는 무기를 구매해야 합니다.
예를 들어, 15번으로 지정된 기사단원은 15의 약수가 1, 3, 5, 15로 4개 이므로, 공격력이 4인 무기를 구매합니다. 만약, 이웃나라와의 협약으로 정해진 공격력의 제한수치가 3이고 제한수치를 초과한 기사가 사용할 무기의 공격력이 2라면, 15번으로 지정된 기사단원은 무기점에서 공격력이 2인 무기를 구매합니다. 무기를 만들 때, 무기의 공격력 1당 1kg의 철이 필요합니다. 그래서 무기점에서 무기를 모두 만들기 위해 필요한 철의 무게를 미리 계산하려 합니다.
기사단원의 수를 나타내는 정수 number와 이웃나라와 협약으로 정해진 공격력의 제한수치를 나타내는 정수 limit와 제한수치를 초과한 기사가 사용할 무기의 공격력을 나타내는 정수 power가 주어졌을 때, 무기점의 주인이 무기를 모두 만들기 위해 필요한 철의 무게를 return 하는 solution 함수를 완성하시오.
- 1 ≤
number
≤ 100,000- 2 ≤
limit
≤ 100- 1 ≤
power
≤limit
문제의 요점을 파악해보자.
number
의 5와 10이 있다.number
까지의 즉, 1, 2, 3, 4, 5의 약수를 구하라 ! )return
한다.조건이 있다.
❗️ 배열에 담은 약수의 갯수가 매개변수 limit
보다 클 경우, 매개변수power
값을 대체해서 더해준다.
function solution(number, limit, power) {
var answer = 0;
let sum = 0;
for(let article = 1; article <= number; article++) {
let result = [];
let i = 1;
while (i <= article) {
if(article % i === 0) {
result.push(i);
}
i++;
}
sum += result.length;
if( limit < result.length) {
sum -= power;
}
}
return answer = sum;
}
// 1부터 number까지의 약수를 구해서 배열에 담는다.
// 공격력의 제한 수치인 limit이하의 수를 모두 더한 값을 리턴한다.
// 만약, 공격력의 수치가 limit보다 큰 약수의 수가 있다면? 공격력 무기인 power로 대체해 그 값을 더해서 리턴한다.
반복문안에서 새로 조건문으로 limit
값 보다 클 경우 나는 모두 더한 값에서 power
의 수를 빼줬다.
하지만, 코드실행에서는 통과되었지만, 제첨후제출에서는 통과하지 못했다.
다른 방법을 생각해 내야겠다.
다른 사람들의 풀이를 보면서 그 풀이를 해석하고 분석해 보면서 왜 이렇게 했는지를 생각했다.
요점은 나는 약수를 구하려했고, 다른 사람들은 약수를 얼마만큼 빠르게 구하는가를 생각한 것에 대해서 조금은 달랐다.
function solution(number, limit, power) {
var answer = 0;
let count;
for(let article = 1; article <= number; article++) {
count = 0;
let i = 1;
// 약수는 대상을 제외하고 대상의 2/1 보다 클 수 없기 때문에
// 반만 테스트 진행 하면 된다.(시간 단축)
while(i <= article/2) {
if(article % i === 0) {
count++;
}
i++;
}
// 반을 나눈다는것은 본인은 제외 한것임으로 카운터에 1을 더해준다
count++;
// 조건문을 삼항연산자로 요약한 방법이다.
answer += count > limit ? power : count
// 처음에 이해 되지 않았던 부분인데
// count가 더 클 경우(예외의 경우)를 먼저 조건에 걸러주고 나서 else로 나머지의 조건에 충족값을 더해준다.
// if(count > limit){
// answer += power;
// }else{
// answer += count;
// }
}
return answer;
}
function solution(number, limit, power) {
let resultArr = [];
let res;
for (let i = 1; i <= number; i++) {
let temp = [];
for (let j = 1; j <= Math.sqrt(i); j++) {
if (i%j === 0) temp.push(j);
}
res = temp.length;
for (let k = 0; k < res; k++) {
temp.push(i/temp[k]);
}
resultArr.push(new Set(temp).size);
}
res = 0;
for (let i = 0; i < resultArr.length; i++) {
if (resultArr[i] > limit) res += power;
else res += resultArr[i];
}
return res;
}
느낀점
나는 약수를 구해서
배열에 담은 길이로 풀었던 거 같은데,,
다른 사람들은 count
와 같은 변수를 만들어 거기에 숫자를 담아줬다.
나도 처음에는 그렇게 했는데 값을 보고 원하는 수가 찍히지 않아서 배열에 담는 것으로 변경했는데 다시 문제의 요점과 흐름을 해석을 해보아야될 것 같다.
문제풀이2에서는 이중 반복문에서 /2
를 했을 때가 헷갈렸는..
거기에 count
를 ++
해주는 부분의 값이 이해가 안되는데 이 부분은 다시 한번 파악해야 되겠다.
문제풀이4에서는 중복을 없애는 Set
을 사용한 것을 보고 .. 내가 아직 많이 부족하구나 생각했다.
그래도 하려는 방법과 제일 비슷했던 풀이지 않나 싶다.
약수를 구하는 방법 중에 제곱근함수로 구하는 방법도 많이 사용되는 것 같다.
reduce
map
을 사용해서 푼 사람들도 있었는데 ,, 리스펙이다.