Cím: Mathematica
Szerző(k):  Lóczi Lajos 
Füzet: 2002/szeptember, 351 - 357. oldal  PDF file
Témakör(ök): Szakmai cikkek

A szöveg csak Firefox böngészőben jelenik meg helyesen. Használja a fenti PDF file-ra mutató link-et a letöltésre.

Idén, 2002-ben ünnepli 14. születésnapját a Mathematica. E kezdetben Stephen Wolfram nevéhez fűződő számítógépes matematikai programot az évek során kiváló szakemberek tucatjai fejlesztették tovább (jelenleg a 4.1-es verziónál tartunk), s mára a legbonyolultabb számítógépes rendszerek között tartják számon. Felhasználói tábora meghaladja az egymilliót és szinte minden tudományterület képviselői megtalálhatók közöttük. Sokoldalúságának és teljesítményének köszönhetően a kutatásban és az iparban egyaránt használják. Kétszáznál több könyv és tucatnyi Mathematica-hoz (sőt, magában Mathematica-ban) írt programcsomag, alkalmazás látott napvilágot.
Mindez annak tudható be, hogy a Mathematica éppúgy alkalmas nagypontosságú számítások gyors elvégzésére, mint szimbolikus (pl. algebrai) kifejezések és objektumok kezelésére. A legkülönfélébb két- és háromdimenziós ábrák, grafikonok készíthetők segítségével. A Mathematica egyben logikusan átgondolt és felépített programnyelv is: rugalmassága éppen abban rejlik, hogy a sok száz beépített matematikai függvényt, illetve utasítást szabadon ötvözhetjük a saját magunk által megírottakkal.
A Mathematica-ról e jelen bevezetőnél bővebb ismertetőt tartalmaz az [1] cikk. Részletes magyar nyelvű útmutató a program használatáról a [2] könyv. Wolfram [3] könyve teljességre törekszik. Elmélyülve a Wolfram Research [4] honlapján, rengeteg érdekes információra lelhetünk. Szintén ők működtek közre az [5] (folyamatosan bővülő) internetes matematikai enciklopédia elkészítésében. Egy új kezdeményezés, a webMathematica segítségével a böngészőprogramok által internetről futtatható Mathematica-alkalmazások hozhatók létre. Ezzel kapcsolatban a [6] és [7] webcímre utalunk.
Kedvcsinálóul néhány (önkényesen, s semmiképpen sem szisztematikusan választott) feladatot oldunk meg a Mathematica segítségével. A feladatok rövidek és inkább csak illusztratív jellegűek, összetettebb problémák részekre bontásakor azonban sok-sok ehhez hasonlóval találkozhatunk. A megoldásokhoz rövid magyarázatot fűzünk, ezekkel igyekszünk megvilágítani egy-egy parancs működését. Az általunk begépelendő parancsokat írógépbetű-típussal emeltük ki.

 
Példák
 

 
1. Hozzuk egyszerűbb alakra a
(2+3+2-3)(5+21-5-21)
kifejezést.
 

A Mathematica fő egyszerűsítő parancsát
FullSimplify[(2+3+2-3)(5+21-5-21)]
használva eredményül 6 adódik. Figyeljük meg, hogy a Mathematica különbséget tesz a kis- és nagybetűk között. A beépített parancsnevek nagy kezdőbetűvel írandók. Függvény- és parancsargumentumok megadásakor szögletes zárójelet kell használnunk.
 
2. Írjuk fel a cos4x+sin5x kifejezést az egyszeres szögek szögfüggvényei segítségével.
 

A TrigExpand[Cos[4 x]+Sin[5 x]] utasítás eredményeként
Cos[x]4+5Cos[x]4Sin[x]-6Cos[x]2Sin[x]2-10Cos[x]2Sin[x]3+Sin[x]4+Sin[x]5
adódik.
 
3. Bontsuk szorzattá az előbbi kifejezést.
 

A TrigFactor[%] parancs hatására ezt kapjuk (a % jel az előző eredményt jelenti):
-(Cos[x2]+Sin[x2])2(-1+2Sin[x])(1+2Sin[3x])
(Melyik utasítással nyerhető vissza ebből az eredeti cos4x+sin5x alak?)
 
4. Adjuk meg cos3 pontos értékét.
 

A Mathematica FullSimplify[FunctionExpand[Cos[3 Degree]]] utasítása az alábbi legegyszerűbb alakot adja meg:
1212(4+7+5+6(5+5))

 
5. Alakítsuk szorzattá az x15-1 polinomot.
 

A Factor[x15-1] utasítás 4 tényezőre bontja polinomunkat:
(-1+x)(1+x+x2)(1+x+x2+x3+x4)(1-x+x3-x4+x5-x7+x8)
Ebben a felbontásban minden együttható racionális szám. Ha a racionális számtestet a 5 elemmel bővítjük,
Factor[x15-1,Extension5]
a polinom tovább bontható:
116(-1+x)(-2-x+5x-2x2)(1+x+x2)(2+x+5x+2x2)(-2+x+5x-x2-5x2+x3+5x3-2x4)(2-x+5x+x2-5x2-x3+5x3+2x4).

 
6. Adjuk meg a 267-1 szám prímtényezős felbontását.
 

A FactorInteger[267-1] parancs ezt adja:
{{193707721,1},{761838257287,1}}
azaz 267-1 felírható, mint két óriási prímszám (nevezetesen 193707721 és 761838257287) első hatványának szorzata.
 
7. Oldjuk meg az x+y+z=2, xy+xz+yz=-5, xyz=-6 egyenletrendszert.
 

Ezt a Mathematica-ban így tehetjük meg:
Solve[x+y+z==2 && x y+x z+y z==-5 && x y z==-6]
A Mathematica a dupla egyenlőségjellel vizsgálja két kifejezés egyenlőségét, a szimpla egyenlőségjel változó értékének definiálására szolgál. A && jel jelenti a logikai és műveletét. A változóneveket nem írhatjuk egybe, a szóköz jelenti a szorzást. Megoldásként egy listában a változók mind a hat lehetséges sorrendjét megkapjuk:
{{x-2,y1,z3},{x-2,y3,z1},{x1,y-2,z3},{x1,y3,z-2},{x3,y-2,z1},{x3,y1,z-2}}

 
8. Oldjuk meg az ax2+bx+c=0 egyenletet, ahol a, b, c tetszőleges számok.
 

A Reduce[a x2+b x+c==0,x] parancs eredménye:
x==-b-b2-4ac2a&&a0||x==-b+b2-4ac2a&&a0||a==0&&b==0&&c==0||a==0&&x==-cb&&b0
A Reduce parancsot használtuk, amely paramétert is tartalmazó egyenlet általános megoldását adja meg. A Solve utasítás csak az ún. generikus megoldásokat adná meg, jelen esetben csak a másodfokú egyenlet megoldóképletét, ami az a=0 esetben nem lenne megfelelő. A || jel jelenti a logikai megengedő vagy műveletét. (Ennek prioritása alacsonyabb az és (&&) műveleténél, ezért nem szükségesek zárójelek). A fenti eredmény értelmezése tehát: ha a0, akkor x egyenlő a másodfokú egyenlet két megoldásával; ha a=0, de b0, akkor az elsőfokú egyenlet megoldóképletét kapjuk vissza; végül, ha a=b=c=0, akkor x-re nincs megkötés.
 
9. Tudjuk, hogy a+b+c=1, a2+b2+c2=2 és a3+b3+c3=3. Mennyivel egyenlő ekkor a5+b5+c5?
 

Eliminate[{mennyi==a5+b5+c5, a+b+c==1, a2+b2+c2==2, a3+b3+c3==3},{a,b,c}]
Erre ezt kapjuk:
mennyi==6
Az Eliminate utasítás ugyanis kiküszöböli a felsorolt egyenletekből a megadott változókat (jelen esetben a, b, c-t). Ami megmarad, éppen az ötödik hatványösszeg. (Hogyan oldható meg a feladat általánosabban: a jobb oldalakon álló 1, 2, 3 számok helyett α, β, γ paraméterekkel?)
 
10. Határozzuk meg (a+b+c+d)17-ben a3b13d együtthatóját.
 

Egy lehetséges megoldást ad az alábbi utasítás:
Coefficient[Expand[(a+b+c+d)17], a3b13d]
A kifejezést az Expand bontja ki. Az eredmény 9520.
 
11. Igazoljuk, hogy (k=1nk)2=k=1nk3, tetszőleges n1 természetes szám esetén.
 

Az állítást a
Sum[k, {k, 1, n}]2== Sum[k3, {k, 1, n}]
parancs eredményeként adódó True (azonosan igaz logikai érték) bizonyítja. (Természetesen a Mathematica-val külön-külön kiszámolva a két oldalt (14n2(1+n)2) magunk is megállapíthatjuk azok egyenlőségét.)
 
12. Oldjuk meg az ||x-1|-1|+||x|-4|<3 egyenlőtlenséget.
 

Ehhez először betöltjük az < <Algebra`InequalitySolve` csomagot. Ezután az
InequalitySolve[Abs[Abs[x-1]-1]+Abs[Abs[x]-4]<3, x]
parancs adja meg a megoldást: 32<x<92.
 
13. Határozzuk meg a 0y-x22 és a -5x5, 0y5 egyenlőtlenségekkel határolt síkbeli tartomány területét.
 

A tartomány speciális alakja miatt olvassuk be a < <Calculus`Integration` csomagot. Ezután a keresett terület a következő határozott integrállal számolható ki:
Integrate[Boole[0    y-x2  2], {x, -5, 5}, {y, 0, 5}]
Az eredmény -43+2053 lesz.
Magát a tartományt egyébként a < <Graphics`InequalityGraphics` csomag beolvasása után az InequalityPlot[0 y-x2 2, {x, -5, 5}, {y, 0, 5}] utasítás rajzolja ki.
 
 

1. ábra
 

A Boole logikai függvény értéke ott 1, ahol a megadott egyenlőtlenség fennáll, másutt zérus. Ez a Plot3D[Boole[0 y-x2 2], {x, -5, 5}, {y, 0, 5}] paranccsal szemléltethető.
 
 

2. ábra
 

 
14. Hozzuk egyszerűbb alakra a ,,(ha A, akkor B) és (A vagy B)'' logikai állítást.
 

A LogicalExpand[Implies[A, B] && (A || B)] parancs eredménye értelmében a fenti állítás logikailag egyenértékű a B állítással.
 
15. Adjuk meg azon pozitív egészeket, melyek egyszerre n4+n2 és k3+1 alakúak, alkalmas 1n104, 1k104 pozitív egészekkel.
 

Az alábbi parancs
Intersection[Table[n4+n2, {n, 1, 10000}], Table[k3+1, {k, 1, 10000}]]
két megoldást szolgáltat:
{2,1332}
(Ellenőrzés: 14+12=2=13+1, illetve 64+62=1332=113+1.) A megoldás során két, a kívánt alakú számokból álló listát hozunk létre, majd vesszük ezen listák (vagy ha tetszik, halmazok) metszetét. Tudnánk még ilyen tulajdonságú számokat találni?
 
16. 1 és 10000 között 4k+1 vagy 4k+3 alakú prímből van több?
 

A 4k+1 alakú, 10000-nél kisebb prímek száma 609, míg a 4k+3 alakúaké 619, amint ezt az alábbi parancsok kiszámolják:
Length[Select[Range[10000]], (PrimeQ[#] && Mod[#,4]==1)&]Length[Select[Range[10000]], (PrimeQ[#] && Mod[#,4]==3)&]
Vegyük szemügyre például az első sort. A Select parancs egy listába gyűjti ki azokat az elemeket a Range[10000] által létrehozott {1,2,...,10000} listából, melyeket # helyébe helyettesítve a
,,(prím-e  #) és (4-gyel maradékosan osztva 1-et ad-e maradékul  #)''
nyitott mondatban igaz értéket kapunk. (Az ilyen nyitott mondatot vagy függvényt a Mathematica-ban tiszta függvénynek nevezzük. A tiszta függvényt & jellel kell lezárnunk.) Végül a Length megszámolja, hány elemet tartalmaz e kiválogatott lista.
 
17. Előfordul-e valahol a π szám tizedestört alakjában az 1234 szám?
 

Erre a kérdésre számítógép nélkül aligha válaszolhatnánk. A Mathematica-val a megoldás elegáns: az 1234 sorozat már az első 15000 jegy között előfordul, mert a
StringMatchQ[ToString[N[π, 15000]], "*1234*"]
parancs True, azaz igaz értéket ad. Az N függvénnyel először meghatároztuk π értékét 15000 jegy pontossággal, ezt karakterlánccá alakítottuk át, majd megnéztük, ez tartalmazza-e valahol az "1234" jelsorozatot. Azt is meg tudjuk mondani, hogy pontosan hol: a
StringPosition[ToString[N[π, 15000]], "1234"]
utasítás eredménye {{13809,13812}}, tehát π jegyei között az "1234" szám a tizedesvessző után először a 1380713810. helyen fordul elő. (Figyelembe vettük ugyanis, hogy a karakterlánccá alakított π-jegyek első két tagja a 3-as és maga a tizedespont.) Meg tudnánk-e oldani a feladatot úgy is, hogy nem alakítjuk át a tizedesjegyeket karakterlánccá?
 
18. Hány nullára végződik 1000 faktoriálisa?
 

E jól ismert kérdésre két megoldást is adunk, a válasz egyébként 249. Az első megoldás egy ciklus segítségével számol:
a=1000!;n=0;While[a10Integers, n++; a=a10];n
Az értékadások után addig osztjuk az 1000! számot 10-zel, amíg csak egész az eredmény. Minden egyes osztáskor eggyel növeljük n értékét, így a nullák számát az n változó tartalmazza a ciklus végén, amit ki is íratunk. (A pontosvessző teszi lehetővé, hogy több utasítást írjunk egymás után egy sorba.)
Második megoldásunk általánosabb. Egy f függvényt definiálunk, mely tetszőleges, 4-nél nagyobb egész számot elfogad bemenetként, majd megadja, hogy hány nullára végződik n faktoriálisa:
f[n_Integer/;n>4] := Length[Split[IntegerDigits[n!]][[-1]]]
Először n! számjegyeit az IntegerDigits segítségével egyesével egy listába tesszük. E listát a Split olyan részlistákra bontja, melyek az eredeti lista egymás után álló azonos elemeiből állnak. Ennek vesszük utolsó elemét a [[-1]] utasítással (az n>4 feltétel garantálja, hogy valóban nullák állnak hátul), majd meghatározzuk az így adódó lista hosszát. (Például a Split[IntegerDigits[10!]] eredménye a {{3},{6},{2},{8,8},{0,0}} lista, melynek utolsó eleme {0,0}.) f[1000] eredménye természetesen ezzel a módszerrel is 249.
 
19. Írjunk függvényt egy szám faktoriálisának kiszámítására.
 

A számtalan lehetőség közül egy hatékony megoldást szolgáltat az alábbi definíció:
faktorialis[n_/; nIntegers && n1] := Apply[Times, Range[n]]
Hogy megvilágítsuk a definíció jobb oldalának működését, tekintsük az n=3 esetet. Ekkor Range[3] értéke az {1,2,3} lista (melyet a Mathematica List[1,2,3] alakban tárol). Ennek fejét, azaz a List szót az Apply parancs Times-ra, azaz a szorzásra cseréli. Viszont Times[1,2,3] eredménye 123, azaz 6.
 
20. Írjuk meg a komplexgyokrajzolo függvényt, melynek bemenete egy egyváltozós polinom, eredménye pedig e polinom gyökeinek képe a komplex számsíkon.
 

A Mathematica-ban mindez egyetlen összetett utasításként megvalósítható:
komplexgyokrajzolo[polinom_] := ListPlot[Cases[NSolve[polinom==0][[All, 1, 2]],    z:(_Complex|_Real){Re[z], Im[z]}], PlotStylePointSize[0.03]]
A nullára rendezett egyenletet először numerikusan megoldjuk (NSolve). Az eredmény egy (általában) komplex számokat tartalmazó speciális szerkezetű lista. A komplex számok közvetlenül még nem ábrázolhatók. Ezért e számokat rendre kigyűjtjük (erre szolgál az [[All, 1, 2]] operátor), majd (a valós-képzetes résznek megfelelően) valós koordináta-párokká alakítjuk, és egy új listában helyezzük el őket (ezt a Cases teszi meg). Végül ábrázoljuk ezt az új listát (ListPlot). (Mivel a Mathematica által választott pontméretet kicsinek találtuk, a PointSize segítségével megnöveltük a pontok méretét). Mindez az x5+x2+2 polinomra alkalmazva a 3. ábrán látható módon fest.
 
 

3. ábra
 

Végül az x5+nx2+2 egyenlet gyökeit ábrázoltuk, amint n (-5)-től 5-ig fut, 110-es lépésekben (4. ábra).
 
 

4. ábra
 

 
Hivatkozások
 

[1] Lóczi Lajos: A Mathematica első évtizede, Természet Világa, 129. évf. 11. sz. (1998) 515‐518. oldal
[2] Szili László ‐ Tóth János: Matematika és Mathematica, ELTE Eötvös Kiadó, Budapest, 1996.
[3] Stephen Wolfram: The Mathematica Book, 4th edition, Wolfram Media/Cambridge University Press, 1999.
[4] www.wolfram.com
[5] mathworld.wolfram.com
[6] www.integrals.com
[7] www.wolfram.com/products/webmathematica/examples