• Keine Ergebnisse gefunden

Beim regelbasierten Zugang wird die im funktionalen Zugang notwendige Code-Redundanz vermieden, indem der Transformationsvorgang alsApply(Expression, Rules) aus einem allgemeinen Programmteil und einem speziellen Datenteil aufgebaut wird.

Der Datenteil Rulesenth¨alt die jeweils konkret anzuwendenden Ersetzungsregeln, also In-formationen dar¨uber, welche Kombinationen von Funktionssymbolen wie zu ersetzen sind.

Der ProgrammteilApply, derSimplifikator, stellt die erforderlichen Routinen zur Musterer-kennung und Unifikation bereit.

Der Simplifikator Applyist also eine zweistellige Funktion, welche einen symbolischen Ausdruck A und einen Satz vonTransformationsregeln ¨ubergeben bekommt und diese Regeln so lange auf A und die entstehenden Folgeausdr¨ucke anwendet, bis keine Ersetzungen mehr m¨oglich sind. Im Gegensatz zum funktionalen Zugang sind hier der Simplifikator und die jeweils anzuwendenden Regels¨atze voneinander getrennt, was es auf einfache Weise erm¨oglicht, Regels¨atze zu erg¨anzen und f¨ur spezielle Zwecke zu modifizieren und anzupassen.

Damit enth¨alt die Programmiersprache eines CAS neben funktionalen und imperativen auch Ele-mente einer logischen Programmiersprache. Wir werden uns in einem sp¨ateren Abschnitt genauer mit der Funktionsweise eines solchen Regelsystems vertraut machen. An dieser Stelle wollen wir uns anschauen, welche Regeln Reduce zum Simplifizieren verschiedener Funktionen kennt. Die jeweiligen Regeln sind unter dem Funktionssymbol als Liste gespeichert und k¨onnen mit der Funk-tionshowrulesausgegeben werden:

showrules log;

{log(1) => 0, log(e) => 1, log(e^~x) => x,

df(log(~x),~x) => 1/x,

df(log(~x/~y),~z) => df(log(x),z) - df(log(y),z)}

Die ersten beiden Regeln ersetzen spezielle Kombinationen von fest vorgegebenen Symbolen durch andere. Solche Regeln werden auch alsspezielle Regelnbezeichnet, denn in ihnen sind alle Bezeich-ner nur in ihrer literalen Bedeutung pr¨asent.

Anders in den beiden letzten Regeln, in denen Bezeichner auch als formale Parameter vor-kommen, die als Platzhalter f¨ur beliebige Teilausdr¨ucke auftreten. So vereinfacht Reduce etwa log(exp(A)) zu A, egal wie der Teilausdruck A beschaffen ist. Der Bezeichnere steht dagegen f¨ur das Symbole in seiner literalen Bedeutung. Wir haben also auch hier zwischen Bezeichnern in ihrer literalen Bedeutung (als Symbolvariable) (neben e sind das in obigen Regeln die Funk-tionssymbole df und log) und Bezeichnern als Wertcontainer (hier: als formale Parameter) zu unterscheiden. Regeln mit formalen Parametern werden auch alsallgemeine Regelnbezeichnet.

Ein solches Regelsystem kann durchaus einen gr¨oßeren Umfang erreichen:

showrules sin;

{sin(pi) => 0, sin(pi/2) => 1,

sin(pi/3) => sqrt(3)/2, sin(pi/4) => sqrt(2)/2, sin(pi/6) => 1/2,

sin((5*pi)/12) => sqrt(2)/4*(sqrt(3) + 1), sin(pi/12) => sqrt(2)/4*(sqrt(3) - 1),

sin((~(~ x)*i)/~(~ y)) => i*sinh(x/y) when impart(y)=0, sin(atan(~u)) => u/sqrt(1 + u**2),

sin(2*atan(~u)) => 2*u/(1 + u**2),

sin(~n*atan(~u)) => sin((n - 2)*atan(u))*(1 - u**2)/(1 + u**2) + cos((n - 2)* atan(u))*2*u/(1 + u**2) when fixp(n) and n>2, sin(acos(~u)) => sqrt(1 - u**2),

sin(2*acos(~u)) => 2*u*sqrt(1 - u**2), sin(2*asin(~u)) => 2*u*sqrt(1 - u**2),

sin(~n*acos(~u)) => sin((n - 2)*acos(u))*(2*u**2 - 1)

+ cos((n - 2)*acos(u))*2* u*sqrt(1 - u**2) when fixp(n) and n>2, sin(~n*asin(~u)) => sin((n - 2)*asin(u))*(1 - 2*u**2)

+ cos((n - 2)*asin(u))*2* u*sqrt(1 - u**2) when fixp(n) and n>2, sin((~x + ~(~ k)*pi)/~d) => sign(k/d)*cos(x/d)

when x freeof pi and abs(k/d)=1/2, sin((~(~ w) + ~(~ k)*pi)/~(~ d)) =>

(if evenp(fix(k/d)) then 1 else - 1)*sin(( w + remainder(k,d)*pi)/d) when w freeof pi and ratnump(k/d) and abs(k/d)>=1,

sin((~(~ k)*pi)/~(~ d)) => sin((1 - k/d)*pi) when ratnump(k/d) and k/d>1/2, sin(asin(~x)) => x,

df(sin(~x),~x) => cos(x)}

Manche der angegebenen Regeln sind noch konditional untersetzt , d. h. werden nur dann ange-wendet, wenn die Belegung der formalen mit aktuellen Parametern noch Zusatzvoraussetzungen erf¨ullt. Diese Effekte sind von regelorientierten Programmiersprachen wie etwa Prolog aber gut bekannt.

Konzeptionelle Anforderungen

1. Transformationen von Ausdr¨ucken k¨onnen ¨uber Regelanwendungen realisiert werden.

Dazu muss das CAS eineMustererkennung(pattern matcher) zur Lokalisierung entspre-chender Anwendungsm¨oglichkeiten sowie der Zuordnung von Belegungen f¨ur die formalen Parameter bereitstellen.

2. Wie bei Funktionen ist zwischenRegeldefinitionundRegelanwendungzu unterscheiden.

3. Wie bei Funktionen k¨onnen in Regeldefinitionen formale Parameter auftreten. Bei Bezeich-nern in einer Regeldefinition ist zu unterscheiden, ob der Bezeichner literal als Symbol f¨ur sich selbst steht oder als formaler Parameter eine Platzhalterfunktion hat.

In den Systemen werden Bezeichner, die als Platzhalter verwendet werden, besonders ge-kennzeichnet. Dies kann am einfachsten geschehen, indem diese Bezeichner in einer separaten Liste (u1, . . . , un) zusammengefasst werden.

4. Im Gegensatz zu Funktionen kann die Anwendung einer passenden Regel konditional sein, d. h. vom Wert eines vorab zu berechnenden booleschen W¨achterbedinung (guard clause) abh¨angen.

Eine Regeldefinition besteht damit aus vier Teilen:Rule(lhs, rhs, bool)(u1, . . . , un) Mathematica lhs /; bool → rhs

Maxima tellsimpafter(lhs, rhs, bool) MuPAD Rule(lhs, rhs, bool)

Reduce lhs => rhs when bool

5. Regelanwendungen haben viel ¨Ahnlichkeit mit der Auswertung von Ausdr¨ucken. Insbeson-dere ist zwischen einfachen Regelanwendungen und iterierten Regelanwendungen zu unter-scheiden.

6. Das Ergebnis h¨angt sowohl von der Reihenfolge der Regelanwendungen als auch von der Strategie der Mustererkennung ab.

Diese Regeln werden automatisch angewendet, wennReducedas Funktionssymbolsinin ei-nem Ausdruck antrifft. So werden etwa mit den Regel 9 bis 11 Ausdr¨ucke der Form

sin(n·arctan(x)) aufgel¨ost.

sin(5*atan(x));

x5−10x3+ 5x

√x2+ 1 (x4+ 2x2+ 1)

Dasselbe Ergebnis kann man mitMuPAD er-reichen, da die Definition vonsindie Informa-tion enth¨alt, dass

sin(arctan(x)) = x

√1 +x2

gilt, wie an diesem Quelltextfragment zu erken-nen ist.

expose(sin) ...

of "arctan" do

return(op(x)/sqrt(1 + op(x)2))

Allerdings muss dazu ¨uber expand erst eine Transformation angestoßen werden, welche die Funktionssymbole sin und arctan unmittel-bar zusammenbringt, indem die Mehrfachwin-kelausdr¨ucke aufgel¨ost werden.

sin(5*arctan(x));

sin(5 arctan(x)) expand(%);

x5

(1 +x2)5/2 − 10x3

(1 +x2)5/2 + 5x

√1 +x25/2 normal(%);

x5−10x3+ 5x (1 +x2)5/2

Zusammenhang mit anderen CAS-Konzepten

Regelanwendungen haben viel ¨Ahnlichkeit mit der Auswertung von Ausdr¨ucken:

• Nach einmaliger Regelanwendungen kann es sein, dass dieselbe oder weitere Regeln anwend-bar sind bzw. werden. Es ist also sinnvoll, Regeln iteriert anzuwenden.

• Iterierte Regelanwendungen bergen die Gefahr von Endlosschleifen in sich.

• Auswertungen k¨onnen als Spezialfall von Regelanwendungen betrachtet werden, da die Ein-tr¨age in der Symboltabelle als spezielles Regelwerk aufgefasst werden k¨onnen.

Regelanwendungen k¨onnen wie Wertzuweisungen lokal oder global vereinbart werden.

• Globale Regeldefinitionen erg¨anzen und modifizieren das automatische Transformationsver-halten des Systems und haben damit ¨ahnliche Auswirkungen wie globale Wertzuweisungen.

• Lokale Regelanwendungen haben viel ¨Ahnlichkeit mit der Substitutionsfunktion, indem sie das regelbasierte Transformationsverhalten auf einen einzelnen Ausdruck beschr¨anken.

• Substitutionen und Wertzuweisungen k¨onnen als spezielle Regelanwendungen formuliert wer-den. Einige CAS realisieren deshalb einen Teil dieser Funktionalit¨at ¨uber Regeln.

• Das gleiche gilt f¨ur Funktionsdefinitionen. Diese k¨onnen als spezielle Regeldefinitionen rea-lisiert werden.

Substitution wird als lokale Regelanwendung realisiert (Mathematica)

expr /. x -> A

Wertzuweisung ohne Auswertung wird als glo-bale Regelanwendung realisiert (Reduce).

let x=A

Mischung von Funktionsdefinition und global vereinbarter Regel (Mathematica).

Zun¨achst wird die Funktion f : x → x2 + 1 definiert. Diese ist als Regel dem Symbolf zu-geordnet.

f[x ]:=x^2+1;

?f

Global‘f

f[x ] := x^2 + 1

f[a+b]

1 + (a+b)2 Nun wird zus¨atzlich eine Regel f¨urf definiert,

die f (mathematisch nicht korrekt) als linea-res Funktional ausweist. Diese Regel ist dem Symbol auf dieselbe Weise zugeordnet wie die Funktionsdefinition.

Die Regeln werden intern sortiert, zun¨achst die Summenregel und erst danach die Funktionsde-fintionsregel angewendet. W¨are die zweite Re-gel zuerst angewendet worden, so lautete das Ergebnis 1 + (a+b)2.

f[x +y ]:=f[x]+f[y];

?f

Global‘f

f[(x ) + (y )] := f[x] + f[y]

f[x ] := x^2 + 1 f[a+b]

2 +a2+b2