function factorize( item, target, arr ){
try{
if( ( typeof target === "undefined" || target === null ) && !Array.isArray(arr) ){
return factorize(parseInt(item), Math.ceil(Math.sqrt(parseInt(item))), [parseInt(item)]);
} else{
if( target > 0 ){
if( item % target === 0 ){
arr.push(target);
arr.push(item/target);
}
return factorize(item,parseInt(target-1),arr);
} else {
return Object.keys(arr.reduce((map,item)=>{map[item]=item;return map;},{})).map(item=>parseInt(item));
}
}
} catch(error){
return [-1];
}
return [-1];
}
function sumFactors( factors ){
if( Array.isArray(factors) && factors.length > 1 ){
return factors.slice(0,factors.length-1).reduce((sum,item)=>sum+item,0);
} else {
return 1;
}
}
function perfectNumbers( end, start ){
start = start || 2;
var tuples = [];
if( end > 0 && start < end ){
for( var i = start; i < end; i++ ){
var factors = factorize(i);
tuples.push([i,sumFactors(factors)]);
}
}
return tuples.filter(item=>numberClass(item[0], item[1])===0).map(item=>item[0]);
}
function numberClass( number, properSum ){
return number - properSum;
}
console.time("factorize");
console.log(perfectNumbers(100000));
console.timeEnd("factorize");
function perfectNumberCandidate(i){
return 2**(i-1)*(2**i-1);
}
function generateCandidates(limit){
var result = [];
for( var i = 0; i < limit; i++ ){
result.push(perfectNumberCandidate(i));
}
return result;
}
console.time("candidateFactorize");
console.log(generateCandidates(10).filter(item=>item>1).map(item=>[item,sumFactors(factorize(item))]).filter(item=>numberClass(item[0], item[1])===0).map(item=>item[0]));
console.timeEnd("candidateFactorize");