Legendre-Polynome

Berechnung mit Reihen-Entwicklung

Legendre-Polynome werden als mathematisches Werkzeug zur Lösung zahlreicher physikalischer Aufgaben verwendet. Auf dieser Seite wird die Berechnung von Legendre-Polynomen vorgestellt.
Algorithmen Ausgewählte IT-Rezepte, Iterationen
Legendre Legendre-Polynome als Werkzeug zur Berechnung physikalischer Aufgaben
Visual Basic Programmierung von Legendre-Polynomen mit Visual Basic (VBA)
C/C++ Programmierung von Legendre-Polynomen mit C/C++

Legendre-Polynome

Quelle: Wikipedia
Adrien-Marie Legendre (1752 - 1833) war ein französicher Mathematiker. Er war eine geniale, aber wenig angepasste Persönlichkeit. Das brachte ihn trotz zeitweiliger Anerkennung seiner Leistungen immer wieder in Schwierigkeiten.

Eine seiner größten Leistungen ist die Entdeckung bzw. Formulierung der nach ihm benannten Legendre-Polynome.
Legendre-Polynome berechnen nicht eine bestimmte Aufgabe, sondern werden als allgemeines Werkzeug zur Berechnung verschiedener Aufgaben verwendet.
Details zur Bedeutung und Anwendung findet man im Internet und in der mathematischen Literatur. An dieser Stelle wird ausschließlich ihre praktische Berechnung vorgestellt.
Die Legendre-Polynome bilden eine Reihe
P0, P1, P2, ...
Alle Elemente der Reihe sind Funktionen einer Variablen (hier x)
Das ergibt für ein Argument x eine Reihe von berechenbaren Polynomen
P0(x), P1(x), P2(x), ...
In der Praxis der meisten Anwendungen verwendet man endliche Reihen von Poynomen, deren Elemente jeweils eine bestimmte physikalische Bedeutung zukommt.

Im Gegensatz zu anderen Reihen nimmt die Größe der Elemente im Laufe der Reihe nicht unbedingt ab. Man kann daher die Grenze der Berechnung nicht durch die maximal erreichbare Genauigkeit definieren, sondern berechnet je nach Anwendung genau die vorgegebene Anzahl von Polynom-Elementen.
Integrale Darstellung der Legendre-Polynome
Quelle: Wikipedia
Das Argument darf aus dem Bereich -1...x...+1 stammen, die fortlaufenden Nummern der Elemente sind
n=0; n=1; n=2; ...
Reihen-Darstellung, so wie in den Beispielen dieser Seite verwendet:
Quelle: Wikipedia
Die Variable k wird ganzzahlig von k=0 bis k=k[max] gezählt.
Für n=gerade ist k[max]=n/2
für n=ungerade ist k[max]=(n-1)/2

Liste

nP[n][x]P[n][0.5]
0P[0][x] = 11
1P[1][x] = x0.5
2P[2][x] = (3*x^2 - 1) / 2-0.125
3P[3][x] = (5*x^3 - 3*x) / 2-0.4375
4P[4][x] = (35*x^4 - 30*x^2 + 3) / 8-0.2890625
5 P[5][x] = (63*x^5 - 70*x^3 + 15*x) / 8 0.08984375
6 P[6][x] = (231*x^6 - 315*x^4 + 105*x^2 - 5) / 16 0.3232421875
... usw ...
Für jedes der ersten Legendre-Polynome lässt sich eine einfache Formel angeben, die man im Internet und in der Literatur findet.

Es ist keine Schande, diese Formeln zu verwenden. Allerdings werden die Elemente zunehmend komplizierter. Für eine größere oder unbestimmte Anzahl von Legendre-Polynomen ist daher die 'elegante' Berechnung mit Hilfe einer einzigen allgemeinen Funktion vorteilhaft.

Die Spalte P[n][0.5] gibt die Ergebnisse für ein Argument x=0.5 an (ohne Gewähr) und dient zur Kontrolle eigener Rechnungen.

Kalkulation

Die Verwendung der angegebenen Formeln in einer Tabellen-Kalkulation (LibreOffice, OpenOffice, MS-Excel, ...) ist trivial:
Man trägt den Wert des Arguments x in eine beliebige Zelle ein (z.B. in B1) und ersetzt den Variablen-Namen x durch die Adresse, z.B. zur Berechnung des Polynoms P[2]
=(3*B1^2-1)/2

Auch die Berechnung der allgemein formulierten Reihen-Darstellung ist möglich. Sie erfordert jedoch Geduld und besondere Sorgfalt und ist deshalb den fortgeschrittenen AnwenderInnen vorbehalten:

Erzeugen sie eine Tabelle mit je einer Zeile für jedes k
Berechnen sie in den Spalten die einzelnen Teile von Zähler und Nenner und setzen sie daraus in jeder Zeile 1 Element zusammen.

Legendre-Polynome mit Visual Basic

Die rechts vorgestellte Funktion berechnet 1 Polynom-Element aus den Argumenten n>=0 (ganzzahlig) und -1>=x>=+1
VBA-Funktionen setzt man in Kalkulations-Programmen ein, um die Berechnung schwieriger Funktionen zu vereinfachen.
Die Programmierung lehnt sich zur besseren Übersicht eng an die Formel der ↑ Reihen-Darstellung an. Sie lässt sich stark vereinfachen, sollte für den praktischen Einsatz jedoch um eine strenge Kontrolle (Validierung) der Argumente erweitert werden.

Vor Beginn der For-Schleife werden die Anfangswerte der Variablen festgelegt:
In kmax wird die Anzahl der zu berechnenden Elemente festgelegt.
Der Wert 2n ist für ein bestimmtes Polynom konstant, wird daher vor Beginn der Schleife (nur einmal) berechnet und in der Variablen pow2n gespeichert.
Das Vorzeichen vorz wird auf den Anfangswert +1 gesetzt.
Die Summe wird - wie in jeder ähnlichen Reihen-Entwicklung - auf =0 gesetzt.

In jedem Durchgang der For-Schleife wird 1 element berechnet und zur laufenden summe addiert.
Die beiden im Zähler der Formel angeführten Werte werden in z1 und z2 berechnet, danach in zaehler zusammengefasst.
Die 4 im Nenner der Formel angeführten Werte werden in n1, n2, n3 berechnet und mit pow2n zu nenner zusammengefasst.
Jedes element wird aus Vorzeichen vorz, zaehler und nenner berechnet

Am Ende der Schleife wird der nächste Durchgang vorbereitet: In dieser Funktion genügt dazu die Umkehrung des Vorzeichens vorz

Zuletzt wird das Ergebnis zurückgegeben.
Visual Basic (VBA) Funktion zur Berechnung von Legendre-Polynomen
Function legendre(n As Integer, x As Double) As Double
Dim k, kmax, vorz As Integer
Dim element, n1, n2, n3, nenner As Double
Dim pow2n, summe, z1, z2, zaehler As Double
kmax = (n - (n Mod 2)) / 2
pow2n = 2 ^ n
vorz = 1
summe = 0
For k = 0 To kmax
z1 = my_fakt(2 * n - 2 * k)
z2 = x ^ (n - 2 * k)
zaehler = z1 * z2
n1 = my_fakt(n - k)
n2 = my_fakt(n - 2 * k)
n3 = my_fakt(k)
nenner = n1 * n2 * n3 * pow2n
element = vorz * zaehler / nenner
summe = summe + element
vorz = -vorz
Next k
legendre = summe
End Function

Die verwendete Hilfs-Funktion my_fakt() wird im ↓ nächsten Absatz vorgestellt.
Die rechts vorgestellte Hilfs-Funktion my_fakt() dient zur Berechnung der Fakultät-Funktion mit Visual Basic:
n! = my_fakt(n) = 1 * 2 * 3 * ... * n

Das laufende Produkt wird in der Variablen p berechnet. Wie in allen ähnlichen Fällen wird ein Produkt vor Beginn der Schleife auf den Anfangswert =1 gesetzt.
Hilfs-Funktion my_fakt() zur Berechnung der Fakultäts-Funktion:
Private Function my_fakt(ByVal number As Integer) As Double
Dim i As Integer
Dim p As Double
p = 1
For i = 1 To number
p = p* i
Next
my_fakt = p
End Function

Kalkulation

Das Beispiel zeigt die einfache Anwendung: Das zu verwendende Argument x wird in Zelle B1 eingetragen - hier der Demo-Wert x=0.5
Sie können jeden Wert -1...x...+1 verwenden.

Die Werte der einzelnen Legendre-Polynome werden in Spalte B berechnet. Sie können den Bereich A5:B5 nach unten ausfüllen, um beliebige weitere Legendre-Polynome zu berechnen.

Mit dem Argument x=0.5 sollten genau jene Werte berechnet werden, die zur Kontrolle in der ↑ Liste angeführt sind.
Anwendung als 'Benutzer-definierte Funktion' in einem beliebigen Kalkulations-Programm:
   AB
1x0,5
2  
3nP[n][x]
40=legendre(A4;$B$1)
5=A4+1=legendre(A5;$B$1)
6=A5+1=legendre(A6;$B$1)
...

Legendre-Polynome mit C/C++

Die Programmiersprache → C/C++ erlaubt die Ausführung von Programmen mit maximaler Geschwindigkeit.
Die rechts vorgestellte Funktion berechnet 1 Polynom-Element aus den Argumenten n>=0 (ganzzahlig) und -1>=x>=+1

Alle Legendre-Funktionen dieser Seite sind bewusst so ähnlich wie möglich programmiert, damit man die verwendeten Elemente in allen Programmiersprachen wieder-erkennen und vergleichen kann.

Zuerst wird der zaehler aus den Variablen z1,z2 berechnet, danach der nenner aus n1,n2,n3 und zuletzt das Element zur laufenden summe addiert.

Erfahrene EntwicklerInnen können mehrere Zeilen zusammenfassen und kommen mit weniger Variablen aus. Die Funktion arbeitet jedoch auch dann nicht wesentlich schneller.

Die hier vorgestellte Version verwendet die Potenz-Funktion pow() der Mathematik-Bibliothek. Wenn man diese durch eine selbst programmierte Funktion ersetzt, dann verwendet die Funktion lediglich die 4 Grundrechnungs-Arten.
C/C++ Funktion zur Berechnung von Legendre-Polynomen:
Mathematik-Bibliothek und Deklaration:
#include <math.h>
double legendre(int,double);
Funktion
double legendre(int n,double x) {
int k,kmax,pow2n,vorz;
double summe,z1,z2,zaehler,n1,n2,n3,nenner,element;
kmax = (n-(n%2))/2;
pow2n = pow(2,n);
vorz = 1;
summe = 0.0;
for(k=0;k<=kmax;k++) {
z1 = my_fact(2*n-2*k);
z2 = pow(x,(n-2*k));
zaehler = z1 * z2;
n1 = my_fact(n-k);
n2 = my_fact(n-2*k);
n3 = my_fact(k);
nenner = n1*n2*n3*(double)pow2n;
summe += (double)vorz*zaehler/nenner;
vorz = -vorz;
}
return summe;
}
Anwendung:
int n;
double x,y;
y=legendre(n,x);
Die Berechnung der Fakultät-Funktion (factorial) erfolgt mit Absicht anders als in den meisten dazu vorgeschlagenen Beispielen.

Die Funktion liefert zwar ein ganzzahliges Ergebnis, der Zahlenwert übersteigt jedoch schon bei 8!=40320 die Werte-Grenze von 2-Byte Variablen (2^15=32768). Daher wird das Ergebnis mit dem Typ double berechnet und zurückgegeben.

Die meist angegebene Formulierung als rekursive Funktion ist weder kleiner noch schneller. Die hier verwendete Version ist jedoch für wenig geübte EntwicklerInnen leichter verständlich.
Hilfs-Funktion zur Berechnung der → Fakultät:
Deklaration:
double my_fact(int);
Funktion:
double my_fact(int n) {
int i;
double p;
p=1.0;
for(i=1;i<=n;i++) {p=p*(double)i;}
return p;
}

Ausblick

Die Änderung der vorgestellten Funktion zu einer professionellen Ausführung sollte für erfahrene EntwicklerInnen kein Problem darstellen:

Sichern sie die Funktion gegen jede mögliche Fehlbedienung ab und überlegen sie, welche Reaktion ihre Funktion in derartigen Fällen zeigen sollte.
Auch die Übertragung des Algorithmus in beliebige andere Programmiersprachen sollte keine schwierige Aufgabe darstellen.
Bei Bedarf und Gelegenheit werden an dieser Stelle weitere Funktionen vorgestellt, z.B.:
Javascript erlaubt die Live-Demonstration auf einer Webseite.