Barkóba
A barkóba két függvényből áll. Az egyik generál egy számot, amelyet egy globális változóba tárol el. Ezt el fogjuk érni a másik függvényből is, amelyet azért hívunk meg, hogy tippeljünk.
> | barkobainit:=proc(n::integer)
global secretnumber; secretnumber := (rand() mod n) + 1; "OK" end; |
> | barkoba:=proc(t::integer)
global secretnumber; if t > secretnumber then return("kissebb"); else if t = secretnumber then return("gratula"); else return("nagyobb"); fi; fi; end; |
> | barkobainit(100); |
> | barkoba(10); |
> | barkoba(50); |
> | barkoba(75); |
> | barkoba(63); |
> | barkoba(69); |
> | barkoba(72); |
> | barkoba(74); |
Legnagyobb közös osztó
Euklideszi algoritmus egy rekurzív megvalósítása a következő függvény.
> | sajatgcd:=proc(a::integer,b::integer)
if b=0 then a; else gcd(b,a mod b); fi; end; |
Próbaképp a beépített gcd függvény a legnagyobb közös osztót adja vissza
> | gcd(55,100); |
úgy, mint a mi legnagyobb közös oszó számoló függvényünk.
> | sajatgcd(55,100); |
Birthday paradoxon valószínűsége
Az a valószínűség, hogy van két ember, akik ugyanazon a napon születtek az alábbi képlettel számlható:
> | birthday2:=proc(n::integer,m::integer)
local i; 1-product((n-i)/n,i=1..m-1); end; |
> | birthday2(365,17); |
Az alábbi ábrán a vízszintes tengelyt x-szel jelölve azt a valószínűséget látjuk, hogy 365 nap esetén x ember között lesz két olyan, akik ugyanazon a napon születtek.
> | with(plots):listplot([seq(evalf(birthday2(365,i)),i=1..50)]); |
Warning, the name changecoords has been redefined
> | with(ListTools); |
Warning, the assigned name Group now has a global binding
Szimmetrikus bolyongás
Az alábbi függvény egy lista részletösszegeit írja ki.
> | PartialSums([1,1,1,-1,-1,666]); |
Vegyünk egy szimmetrikus bolyongást. Minden lépésben 1/2 - 1/2 valószínűséggel lépünk fel és le. A következő képpen valósítjuk meg: létrehozunk egy 10 hosszú listát, amelyben minden elem 50%-os valószínűséggel -1, illetve 1, majd ennek vesszük a részletösszegeit. Így olyan, mintha minden egyes lépés után az előzőhöz vagy hozzáadunk 1-et, vagy kivonunk 1-et.
> | listplot(PartialSums([seq(2*(rand() mod 2)-1,i=1..10)])); |
Növelve a lépések számát megfelelő messziségből egy Brown-mozgást látunk. A Brown-mozgás fontos fizikában (részecskemozgás), pénzügyben (tőzsde), valószínűségszámításban.
> | listplot(PartialSums([seq(2*(rand() mod 2)-1,i=1..10000)])); |
Ha 5-ös Maple-t használunk, akkor nem lesz PartialSums függvényünk, úgyhogy írjunk egyet!
> | part:=proc(l::list)
local i,s,r; r:=array(1..nops(l)); s:=0; for i from 1 to nops(l) do s:=s+l[i]; r[i]:=s; od; r; end; |
> | listplot(part([seq(2*(rand() mod 2)-1,i=1..10000)])); |
Rajzolási opciók, függvény iterálás
A plot függvény opcióiról segítséget az alábbi módon kérhetünk. Van egy link erre a plot leírásánál legalul.
> | ?plot,options |
exp@@2 egy olyan függvény exp(exp( )) függvényt jelöli.
> | evalf( (exp@@2)(1) ); |
Az exp@@3 pedig az exp 3-szoros iterációját.
> | evalf( (exp@@3)(1) ); |
Az alábbi grafikonon 1, sin(x), sin(sin(x)), sin(sin(sin(x))), .... látható. A paraméterekkel csak azt érjük el, hogy szebb legyen az ábra.
> | listplot([seq(evalf((sin@@n)(1)),n=1..20)],color=red,axes=boxed,labels=[érték,lépésszám],view=[0..21,0..1],style=point,symbol=cross,symbolsize=20); |
Műveletek listákkal
> | with(ListTools): |
Egy gyorsabb megadási módja a 10-től 20-ig terjedő számoknak
> | l := [$10..20]; |
Az 5 prím.
> | isprime(5); |
A 6 nem prím.
> | isprime(6); |
A select egy lista minden egyes elemére lefuttatja az első paraméterként kapott függvényt, és csak azokat hagyja bent, amelyre a függvény true-val tért vissza.
> | select(isprime, l); |
A remove ugyanazt csinálja, mint a select, épp ellenkezőleg a true-val visszatérő tagokat dobja el.
> | remove(isprime, l); |
A függvényt kicserélhetjük egy általunk megírt függvényre, amelyet megadhatunk így
> | select(proc(x) if x>15 then true; else false; fi; end, l); |
és így is.
> | select(x->if x>15 then true; else false; fi, integers); |
Vegyünk egy egyszerű listát.
> | l:=[1,2,3,4]; |
A Rotate parancs a ListTools csomagban található, a második paraméterben azt kell megadni, hogy hány elemmel fogassa el a listát.
> | Rotate(l,1); |
A Flatten szétszedi az egymásba ágyazott listákat, és 1 listát készít.
> | Flatten([1,2,3,[4,5]]); |
Rendezés.
> | sort([1,4,3,2]); |
Elem vizsgálat.
> | member(1,[1,2,3]); |
Fraktálok
Egy kétváltozós függvény:
> | g:=(x,y)->(x^2,y/2); |
Próbaképp értékeljük ki 1 helyen:
> | g(2,2); |
A Sierpinski háromszöget fogjuk kirajzolni. Az elv a következő: a sierpinski függvénynek 3 paramétert adunk: egy l listát, amelyben az eddig kiszámolt pontok lesznek, illetve 3 függvényt, amely az iterált függvényrendszer elemei. Egy 4 elemű sorozattal tér vissza, amelynek első eleme az általa kibővített lista, a többi 3 eleme pedig a függvény változatlanul. Így alkalmas arra, hogy iteráljuk a sierpinski függvényt, hiszen pont olyan típusú kimenete van, mint amilyen típusú bemenete.
> | sierpinski:=proc(l,g1,g2,g3)
local i; [seq([g1(op(l[i]))],i=1..nops(l)),seq([g2(op(l[i]))],i=1..nops(l)),seq([g3(op(l[i]))],i=1..nops(l))],g1,g2,g3; end; |
> |
Iteráljuk a függvényt 7-szer, és elindítjuk a [0,0] pontból. A legvégén olyan pontokat fog visszaadni, amelyek a [0,0] pontból állíthatóak elő a megadott 3 függvény összesen 7-szeri tetszőleges alkalmazásával.
> | plot( (sierpinski@@7)( [[0,0]],(x,y)->(x/2,y/2),(x,y)->(x/2+1/2,y/2),(x,y)->(x/2+1/4,y/2+sqrt(3)/4))[1], style=point, symbol=POINT, scaling=constrained); |
Általános fraktálszámoló eljárás. A különbség csak annyi, hogy nem 3 függvényt adunk meg neki, hanem egy listát, amelyben függvények vannak.
> | fraktal:=proc(l,g)
local i,j; [seq(seq([g[j](op(l[i]))],i=1..nops(l)),j=1..nops(g))],g; end proc; |
Az előző program átírata a fraktal függvényre.
> | plot( (fraktal@@7)( [[0,0]],[(x,y)->(x/2,y/2),(x,y)->(x/2+1/2,y/2),(x,y)->(x/2+1/4,y/2+sqrt(3)/4)])[1], style=point, symbol=POINT, scaling=constrained); |
Más fraktálok is gyorsan kódolhatóak.
> | plot( (fraktal@@4)( [[0,0]],[(x,y)->(x/3,y/3),(x,y)->(x/3,y/3+1/3),(x,y)->(x/3,y/3+2/3),(x,y)->(x/3+1/3,y/3),(x,y)->(x/3+2/3,y/3),(x,y)->(x/3+2/3,y/3+1/3),(x,y)->(x/3+2/3,y/3+2/3),(x,y)->(x/3+1/3,y/3+2/3)])[1], style=point, symbol=POINT, scaling=constrained); |
A véletlenné tételének egy módszere.
> | veletlenfraktal:=proc(l,g)
local i,j,ret; ret:=[]; for j from 1 to nops(g) do if (rand() mod 3) < 2 then ret := [op(ret),seq([g[j](op(l[i]))],i=1..nops(l))]; fi; od; ret,g; end proc; |
> | plot( (veletlenfraktal@@5)( [[0,0]],[(x,y)->(x/2,y/2),(x,y)->(x/2,y/2+1/2),(x,y)->(x/2+1/2,y/2),(x,y)->(x/2+1/2,y/2+1/2)])[1], style=point, symbol=POINT, scaling=constrained, view=[0..1,0..1]); |
Ez az igazi véltelenítés. Minden esetben feldob egy érmét, és a véletlentől teszi függővé, hogy az adott iterált függvényt meghívja-e. Rekurzívan oldottam meg, a program teljesen máshogyan fut, mint az eddigiek. Az eddigieknél bonyolultabb, nem gond, ha valaki ezt nem érti.
> | veletlenfraktal2:=proc(l,g,n::integer)
local i,j,ret,tr; if n = 0 then return l; fi; ret:=[]; for j from 1 to nops(g) do if (rand() mod 9) < 8 then tr := veletlenfraktal2(l,g,n-1); ret := [op(ret),seq([g[j](op(tr[i]))],i=1..nops(tr))]; fi; od; ret; end proc; |
> | plot( veletlenfraktal2( [[0,0]],[(x,y)->(x/2,y/2),(x,y)->(x/2,y/2+1/2),(x,y)->(x/2+1/2,y/2),(x,y)->(x/2+1/2,y/2+1/2)], 6), style=point, symbol=POINT, scaling=constrained,view=[0..1,0..1]); |
Contourplot
A contourplot-tal szép ábrákat lehet készíteni. A megadott függvény szintvonalait ábrázolja.
> | contourplot(sin(x*y),x=-3..3,y=-3..3); |
Ugyanez 3 dimenzióban.
> | contourplot3d(exp(-(2*x^2+y^2)/2),x=-2..2,y=-2..2); |
> | plot3d(0.3*x^3-x+y^2, x=-2..2, y=-2..2, axes=box, color=0.3*x^3-x+y^2, title=Köbös); |
> | plot3d(sin(x^2+y^2),x=-2.5..2.5,y=-2.5..2.5, axes=box, style=patchcontour); |
Pollard faktorizáló módszere
Azoknak ajánlom a következő programot, akik már találkoztak Pollard faktorizáló módszerével.
> | Pollard:=proc(n::integer,lim::integer)
local i,x,y,k,d; i:=1; x[1]:=(rand() mod n); y:=x[1]; k:=2; while i < lim do i:=i+1; x[i]:= ((x[i-1]^2-1) mod n); d:=igcd(y-x[i],n); if d<>1 and d<>n then return(d); fi; if i=k then y:=x[i]; k:=2*k; fi; od; "Nem sikerült" end; |
> | Pollard(391,100); |