Algorithm

[CodeKata] 프로그래머스 : 3.9(화), 숫자의 표현

ttaeng_99 2021. 3. 9. 16:06
반응형

🥋 Ooooth!! (Level 2)

 

🧮 풀이

공식보다는, 내가 발견한 나름의 규칙성으로 푼 방식이다. 

function solution(n) {
  let answer = 1;
  let div = 2;
  while (Math.round(n/div) - Math.floor(div/2) >= 1) {
    if (div%2 === 1 && n%div === 0) {
      answer++;
    }
    else if (div%2 === 0 && n%div === div/2) {
      answer++;
    }
    div++;
  }
  return answer;
}

1) 변수 설정

  • answer는 연속한 자연수의 경우의 수이다. 1로 시작하는 이유는 n 자체 1개인 경우는 모든 수가 해당하므로!
  • div는 n을 나눌 숫자이다. 위의 경우가 1로 나눴을 떄이므로, 2부터 시작하면 된다.

2) 규칙성 기반 로직

  • 규칙성1 : n을 홀수로 나눌 때, 나머지가 0이면 그 div를 중심으로 연속한 자연수가 가능하다. (15/5 = 3 -> 1+2+3+4+5)
  • 규칙성2 : n을 짝수로 나눌 때, 나머지가 div/2면 연속한 자연수가 가능하다. (14/4 몫 3, 나머지 2 -> 2+3+4+5)
  • 규칙성3 : while 반복문을 순회한다. 종료조건은 Math.round(n/div) - Math.floor(div/2) 가 1 이상일 때이다.
    • 이유는, 연속한 자연수 조합에서, 첫 값이 1이면 더 이상의 카운트는 무의미하다. 
    • 15는 div = 5 가 마지막이다. 이 때, n/div(중앙점)은 3이며, 첫 값인 1까지 차이는 Math.floor(div/2) 인 2이다.
    • 21은 div = 6 이 마지막이다. 이 때, Math.round(n/div)(중앙점)은 4이며, 첫 값인 1까지 차이는 div/2 인 3이다. 

 

🖇 리뷰

프로그래머스 다른 풀이를 참고해보았다. 홀수인 약수의 개수를 구한 방법이나... 이것이 어떻게 정답과 연관되는진 모르겠다.

또한, num의 최대값인 10000까지 순회해야하는 부담이 있는 로직인 것 같다.

function expressions(num) {
    var answer = 0;

  for(var i=1; i<=num; i++) {
    if (num%i == 0 && i%2 == 1)
      answer++
  }
    return answer;
}
반응형