Comment fonctionne-t-il ?
Ceci est la suite de l'implémentation en langage C, fonctionnant avec un Dénominateur quelconque, même non premier. Il sera facilement transposable en tout autre langage (BASIC, Java, PowerBuilder, Oracle, Mapple, MathLab, etc.).
Il permet d'obtenir la longueur de la période des fractions d'un Dénominateur mais encore tous les facteurs du calcul de cette période en base infinie.
long
of_getperiodeNb(long pl_nombre, long pl_base, long pl_Dividende)
{
long
ll_Dividende1;
long
ll_Dividende2;
long
ll_Quotient1;
long
ll_Quotient2;
long
ll_Reste1;
long
ll_Reste2;
long
ll_base1;
long
ll_base2;
long
ll_i;
long
ll_DebFin;
On se propose de calculer la longueur de la période de Dividende/ Nombre en base B+KN , nous aurons donc besoin de deux bases consécutives l'une B1 et l'autre B2 égale à B1+N. Le phénomène des congruences permet de valider ce résultat pour toutes les bases de forme B+KN.
ll_base1
= pl_base%pl_nombre; La première base est tronquée
modulo le nombre.
if
(ll_base1==1) ll_base1 = 1 + pl_nombre; On se permet de
calculer en bases 1+KN
ll_base2
= ll_base1 + pl_nombre; B2=B1+N
ll_Dividende1
= pl_Dividende;
ll_Quotient1
= 0;
ll_Dividende2
= pl_Dividende;
ll_Quotient2
= 0;
On
calcule d'abord jusqu'à la longueur maximale de la période (n-1),
et pour les deux bases B1 et B2.
for
(ll_i = 0L; ll_i < pl_nombre; ll_i++)
{
ll_Reste1
= ll_Dividende1 - ll_Quotient1 * pl_nombre;
ll_Dividende1
= ll_Reste1 * ll_base1;
ll_Quotient1
= long(ll_Dividende1/ pl_nombre);
ll_Reste2
= ll_Dividende2 - ll_Quotient2 * pl_nombre;
ll_Dividende2
= ll_Reste2 * ll_base2;
ll_Quotient2
= long(ll_Dividende2/ pl_nombre);
Et
on met la différence dans un tableau
Nb_PeriodeEntiere[ll_i]
= (int)(ll_Quotient2 - ll_Quotient1);
}
Puis
on remonte le tableau à l'envers, cela évite de prendre en compte
les premiers chiffres parasites empêchant de voir la période comme
par exemple pour 789/810 = 0,97407407407..., où le 9 n'a rien à
voir avec elle.
Nb_LongPeriode
= 0L;
ll_i
= pl_nombre - 1;
ll_DebFin
= (long)Nb_PeriodeEntiere[ll_i]; On
commence à la fin du tableau
do
{
ll_i--;
Nb_LongPeriode++;
A
la fin on aura la longueur de la période
}
while(ll_DebFin
!= (long)Nb_PeriodeEntiere[ll_i]); Dès
que la période se répète, on arrête
Ca
coûte pas plus cher, on ne met qu'un seul exemplaire de la période
dans un autre tableau
for
(ll_i = 0L; ll_i <= (long)Nb_LongPeriode; ll_i++)
Nb_Periode[ll_i]
= Nb_PeriodeEntiere[pl_nombre - Nb_LongPeriode + ll_i - 1];
Là
c'est quand le résultat tombe juste
if
(Nb_LongPeriode==1 && Nb_PeriodeEntiere[pl_nombre - 1]==0)
Nb_LongPeriode
= 0;
On
peut maintenant renvoyer la longueur de la période
return
Nb_LongPeriode;
}