Heel veel sneller dan dit krijg ik die matrix methode denk ik niet:
Code: Selecteer alles
static int matrices[8];
static int a[4];
static int b[4];
void MatrixPower( int n )
{
if (n>1)
{
MatrixPower(n>>1);
// a = a * a
b[0] = a[0];
b[1] = a[1];
b[2] = a[2];
b[3] = a[3];
a[0] = b[0]*b[0] + b[1]*b[2];
a[1] = b[0]*b[1] + b[1]*b[3];
a[2] = b[2]*b[0] + b[3]*b[2];
a[3] = b[2]*b[1] + b[3]*b[3];
}
if (n&1)
{
// a = a * {{1 1}{1 0}}
b[0] = a[0];
b[1] = a[1];
b[2] = a[2];
b[3] = a[3];
a[0] = b[0] + b[1];
a[1] = b[0];
a[2] = b[2] + b[3];
a[3] = b[2];
}
}
int Fib( int n )
{
a[0] = a[3] = 1;
a[1] = a[2] = 0;
MatrixPower(n-1);
return a[0];
}
En als ik die vergelijk met die van mij is de matrixmethode toch zo'n 2.5 keer langzamer.
Indien nog suggesties om een van beide methodes te verbeteren, graag.
Die van mij kan in een hoop gevallen nog wel sneller door slimmer van bitcombinaties gebruik te maken. Bijvoorbeeld
\(x^{15}\)
wordt nu gedaan als
\(x^8x^4x^2x\)
maar dat kan ook met
\((x^5)^3\)
. Wil je dit consistent toepassen dan moet je n opdelen in priemfactoren, en dat gaat niet met
\({\cal O}(\log(n))\)
, en het is me ook ff teveel gepriegel om dat verder te benutten.
Het vage vermoeden dat ik daarstraks had was dat deze twee methoden, zij het vanuit een compleet verschillende benadering / interpretatie, op dezelfde berekening neerkwamen. Maar dat was niet zo.
In theory, there's no difference between theory and practice. In practice, there is.