↑ gigo:
Tvůj kód jsem nezkoumal.
Jenom by mě zajímalo, kde jsi k úloze přišel.
Ono totiž každé racionální číslo tj. číslo tvaru p/q, kde p a q jsou přirozená čísla, je buď celé nebo desetinné bez periody nebo periodické, to znamená, že i podíl 1/983 bude číslo periodické, ovšem jeho perioda bude mít docela dost míst (asi 982)
Jinak abys neřekl, tak tento kód (psáno jako konzolová aplikace v Delphi) by měl pracovat dobře.
Skrytý text:
program Delsper;
{$APPTYPE CONSOLE}
uses
SysUtils{, StrUtils};
var m,n,i,zbytek,cislo,j,m1,n1,p,q,dva,pet,deset,kr:integer;
zakl,des,per:string;
pole:array[1..2000] of string;
hotovo:boolean;
begin
WriteLn('---------------------- Program deleni s periodou ------------------------');
WriteLn;
Write('Zadej dve prirozena cisla z intervalu <1,1000>, oddelena mezerou: ');
Read(n);
Read(m);
hotovo := false;
i := 0;
cislo := n div m;
zbytek := n mod m;
Writeln;
if zbytek=0 then
WriteLn(cislo)
else
begin
Write(cislo,DecimalSeparator);
while (hotovo=false)and(i<=2000) do
begin
Inc(i);
cislo := zbytek*10;
Str(cislo div m,pole[i]);
zbytek := cislo mod m;
if zbytek=0 then
hotovo := true;
end;
if i<6 then
begin
for j := 1 to i do
Write(pole[j]);
WriteLn;
end
else
begin
p := 0; q := 0;
m1 := n; n1 := m;
while m1 mod 2=0 do
begin
m1 := m1 div 2;
p := p+1;
end;
while n1 mod 2=0 do
begin
n1 := n1 div 2;
q := q+1;
end;
if q-p>0 then
dva := q-p
else
dva := 0;
if p>q then
kr := q
else
kr := p;
m1 := n; n1 := m;
for i := 1 to kr do
begin
m1 := m1 div 2;
n1 := n1 div 2;
end;
p := 0; q := 0;
while m1 mod 5=0 do
begin
m1 := m1 div 5;
p := p+1;
end;
for i := 1 to p do
m1 := 5*m1;
while n1 mod 5=0 do
begin
n1 := n1 div 5;
q := q+1;
end;
for i := 1 to q do
n1 := 5*n1;
if q-p>0 then
pet := q-p
else
pet := 0;
if p>q then
kr := q
else
kr := p;
for i := 1 to kr do
begin
m1 := m1 div 5;
n1 := n1 div 5;
end;
p := 0; q := 0;
while m1 mod 10=0 do
begin
m1 := m1 div 10;
p := p+1;
end;
for i := 1 to p do
m1 := 10*m1;
while n1 mod 10=0 do
begin
n1 := n1 div 10;
q := q+1;
end;
for i := 1 to q do
n1 := 10*n1;
if q-p>0 then
deset := q-p
else
deset := 0;
p := dva+pet-deset;
zakl := '';
des := '';
for i := 1 to p do
zakl := zakl+pole[i];
for i := p+1 to 1999 do
des := des+pole[i];
if Length(des)>0 then
begin
i := 2;
while Copy(des,1,i)<>Copy(des,1+i,i) do
i := i+1;
per := '('+Copy(des,1,i)+')';
if Length(per)=4 then
if per[2]=per[3] then
per := '('+per[2]+')';
WriteLn(zakl,per);
end;
end;
end;
ReadLn;
ReadLn;
end.
Princip je takový, že případný počet čísel před periodou je dán jako:
1. zlomek n/m vykrátíme čísly 2 a 5.
2. vykrácený jmenovatel rozložíme na součin prvočísel a spočítáme počet čísel 2 a 5 a také součinů 2.5 (to je kolikrát jde vykrácený jmenovatel dělit beze zbytku 10)
3. Potom počet číslic před periodou je: počet čísel 2+počet čísel 5-počet dělení 10
4. Perioda se potom určí tak, že se hledá shodnost stále se prodlužujících stringů tvořených postupně prvními dvěmi a třetím a čtvrtým znakem periody. Pak se porovnávají 1-3 se 4-6 atd. až se nalezne shoda. Protože se začínají porovnávat stringy délky 2 je možné, že dostaneme periodu dvoumístnou (např. 33). To je pak vyeliminováno tím, že se zjistí zda jsou ve dvoumístné periodě 2 stejé číslice a pokud ano je z ní udělána perioda jednočíslicová.