**BE AWARE** working solution in this post

### Questions

**Object/2-dimensional array dilemma**

Not directly related to working solution, but in earlier versions of code was 2 options:

Use nested array or Use object for {key:value} format.

What logic can be applied when making such decisions?

**Naming options**

In the code below there is function

*getProductOfAllPrimeDivisors*

This name refers to the mathematical nature of function.

Alternative would be

*generateLoopStep*

This name refers to the implementation specifics.

What is the best practice when choosing between these two options.

**Terminal condition**

In this solution I used `for`

loop with empty terminal condition. I could easily set relevant terminal condition. But I decided not to.

Main reason - I can prove by math definitions that in my case terminal condition isn’t necessary at all.

But I still have a suspicion - maybe it’s not best practice?

Any feedback in general would be appreciated.

```
//factorial is definitely multiple of numbers from 1 to n
//UNIT 1:factorial(n)
//input: number output: number
const factorial = (num) => { //??? maybe there are built-in functions for factorial, more efficient
//base case
if (num === 0 || num === 1) {
return 1;
}
//recursive step
else {
return num * factorial(num - 1);
}
}
//if we factorize(factorial(n)) => can get array of its prime divisors
//we will be searching for smallestMult with loop,
//BUT it will be loop with VERY WIDE step
//for the test case smallestMult(5) answer is 60, but loop step will be 30(2*3*5)
//for the test case smallestMult(13) answer is 360360, but loop step will be 30030(!!!!!!)
//we know(from experiments/testing) >>> factorial and smallestMult
//have the same prime divisors
//loop step will be >>> product of all prime divisors of factorial
//technically it will be nested loops
//BUT >>> the bigger size of problem >>> the wider will be loop step
//UNIT(2) getProductOFAllPrimeDivisors(n) //alternative func name generateLoopStep
//input: number output: number
const getProductOfAllPrimeDivisors = (num) => {
let result = 1;
const arrayOfDivisors = []; //need product of only one occurance
//of each prime divisor
while (num !== 1) {
for (let i = 2; i <= num; i++) {
if (num % i === 0) {
num = num / i; //need to reinit.num even if primefactor is a duplicate
if (arrayOfDivisors.indexOf(i) == -1){
//accumulating only if its 1st occurance of prime factor
result *= i;
arrayOfDivisors.push(i);
}
break;
}
}
}
return result;
}
//unit testing
/*
console.log(getProductOfAllPrimeDivisors(120));//30
console.log(getProductOfAllPrimeDivisors(2520));//210
console.log(getProductOfAllPrimeDivisors(24));//6
console.log(getProductOfAllPrimeDivisors(360360));//30030
*/
//UNIT for solution
function smallestMult(n) {
const loopStep = getProductOfAllPrimeDivisors(factorial(n));
for (let i = loopStep;;i+=loopStep) { //can set terminal condition but from math standpoint it makes no sense
for (let j = 1; j <= n; j++) { //lets loop through all divisors >>> can be optimized using array from UNIT2
if (i % j !== 0) { //check not passed>>>get out of inner loop
break;
}
//if we on final iter. step and all checks passed >>> job done
if (n === j) {
return i;
}
}
}
}
//fCC test passed
```