JavaScript (ES6), 65 64 Byte
f=(a,i=1)=>a>i?(c=f(a-i,i+=2))[0]==i?[i-2,...c]:f(a,i):a<i?0:[i]
Gibt ein Array zurück, wenn es eine Lösung gibt, oder 0 für keine Lösung.
Dies ist eine äußerst ineffiziente und dennoch golferische Lösung des Problems.
Es sucht nach der ersten Lösung mit a-i
und i=1
, auch wenn es die rekursive Stapel nicht aufzuarbeiten. Beginnt diese Lösung nicht mit i+2
, suchen wir rekursiv mit a
und nach der ersten Lösung i+2
.
Ungolfed
f=(a,i=1)=>
a > i ?
(c = f(a - i, i += 2))[0] == i ?
[i-2, ...c] :
f(a, i) :
a < i ?
0 :
[i]
Testfälle:
f=(a,i=1)=>a>i?(c=f(a-i,i+=2))[0]==i?[i-2,...c]:f(a,i):a<i?0:[i]
console.log(JSON.stringify(f(1))); //[1]
console.log(JSON.stringify(f(3))); //[3]
console.log(JSON.stringify(f(4))); //[1, 3]
console.log(JSON.stringify(f(5))); //[5]
console.log(JSON.stringify(f(6))); //[0]
console.log(JSON.stringify(f(9))); //[1, 3, 5]
console.log(JSON.stringify(f(15))); //[3, 5, 7]
console.log(JSON.stringify(f(104))); //[23, 25, 27, 29]
Für eine Vorstellung davon, wie ineffizient dies ist, f(104)
erfordert die Lösung 69.535 rekursive Aufrufe. Der Stapel ist nie tiefer als 51 Ebenen, daher kein Problem mit dem Stapelüberlauf.
Die Lösung f(200)
erfordert 8,6 Millionen rekursive Aufrufe mit einem Stack von 99 Ebenen. (Seine Lösung ist [11,13,15,17,19,21,23,25,27,29]
.)
Hier ist eine visuelle Darstellung des laufenden Programms:
r=0;
output=o=>setTimeout(_=>O.textContent += o + '\n', r++ * 20);
f=(a,i=1,s='',o = s + 'a=' + a + '; i=' + i + ';')=>
(
output(o),
a > i ?
(c = f(a - i, i += 2, s + ' '))[0] == i ? (
output(o + ' a > i; [i-2, ...c] = [' + [i-2, ...c] + '];'),
[i-2, ...c]
) : (
output(o + ' a > i; c=[' + c + ']; ' + 'c[0]+2 != i ... dead end\n' + s + 'trying a, i+2:'),
f(a, i, s)
) :
a < i ? (
output(o + ' a < i ... dead end'),
0
) : (
output(o + ' a == i;'),
[i]
)
)
f(21); //[5, 7, 9]
<pre id=O></pre>