14.10.2022, 05:48
Eindimensionale lineare Interpolation
A1: X-Suchwert
B1:C5: X-Werte und Y-Werte (als nebeneinanderliegende Spalten; sonst halt MTRANS mit verwenden)
=LINEAREINTERPOLATION(A1;B1:C5) mit LINEAREINTERPOLATION benennend
=LAMBDA(z;xy;LET(x;INDEX(xy;;1);y;INDEX(xy;;2);c;VERGLEICH(z;x);d;c+1;
(INDEX(y;d)-INDEX(y;c))*(z-INDEX(x;c))/(INDEX(x;d)-INDEX(x;c))+INDEX(y;c)))
Achtung: Die X-Werte müssen aufsteigen. Außerhalb der beiden äußersten Werte gibt es Fehler. Möchte man diese Fehler durch Interpolationsweiterführung umgehen, dann bitte die fette Zuweisung durch folgende 2 Zuweisungen ersetzen: e;VERGLEICH(z;x);c;WENNFEHLER(e-(ZEILEN(x)=e);1);
=LINEAREINTERPOLATION(0;{1.2;8.7;9.9}) ergibt #NV oder bei o.g. Ersatz 1,28571429
=LINEAREINTERPOLATION(10;{1.2;8.7;9.9}) ergibt #BEZUG! oder bei o.g. Ersatz 11
Dann funktioniert die Interpolation genauso wie TREND mit nur 2 Punkten, nur - anders als dort mit nur einer Gerade - mit mehreren aneinandergereihten Geraden, deren beide äußere dann unendlich lang sind.
Zweidimensionale lineare Interpolation
A1: X-Wert
B1: Y-Wert
C1: Beginn der 2D-Tabelle inklusive Vorspalte y und Kopfzeile x
Geht diese 2D-Tabelle bis J9, ermittelt die nachfolgende Funktion (VBA oder LAMBDA)
die Kopfzeile x zu D1:J1 (Horiz)
die Vorspalte y zu C2:C9 (Verti)
die Suchmatrix zu D2:J9 (Matri).
Ist die Tabelle noch nicht in der beschriebenen Form, muss sie zunächst so hergestellt werden.
Public Function Interpolation2Dim(ByVal B As Range, x, y)
Spaln = B.Columns.Count
Zeiln = B.Rows.Count
Horiz = B.Offset(0, 1).Resize(1, Spaln - 1)
Verti = B.Offset(1, 0).Resize(Zeiln - 1, 1)
Matri = B.Offset(1, 1).Resize(Zeiln - 1, Spaln - 1)
i = Application.Match(y, Verti)
j = Application.Match(x, Horiz)
xu = Horiz(1, j + 0): mu = Matri(i + 0, j + 0)
xo = Horiz(1, j + 1): mo = Matri(i + 0, j + 1)
yu = Verti(i + 0, 1): nu = Matri(i + 1, j + 0)
yo = Verti(i + 1, 1): no = Matri(i + 1, j + 1)
mm = (x - xu) / (xo - xu) * (mo - mu) + mu
nm = (x - xu) / (xo - xu) * (no - nu) + nu
nn = (y - yu) / (yo - yu) * (nm - mm) + mm
Interpolation2Dim = nn
End Function
=LINEAREINTERPOLATION2DIM(A1;B1;C1#) mit LINEAREINTERPOLATION2DIM benennend
=LAMBDA(x;y;z;LET(
Horiz;WEGLASSEN(INDEX(z;1;);;1);
Verti;WEGLASSEN(INDEX(z;;1);1;);
Matri;WEGLASSEN(z;1;1);
ii;VERGLEICH(y;Verti);i;WENNFEHLER(ii-(ZEILEN(Verti)=ii);1);
jj;VERGLEICH(x;Horiz);j;WENNFEHLER(jj-(SPALTEN(Horiz)=jj);1);
xu;INDEX(Horiz;j+0);mu;INDEX(Matri;i+0;j+0);
xo;INDEX(Horiz;j+1);mo;INDEX(Matri;i+0;j+1);
yu;INDEX(Verti;i+0);nu;INDEX(Matri;i+1;j+0);
yo;INDEX(Verti;i+1);no;INDEX(Matri;i+1;j+1);
mm;(x-xu)/(xo-xu)*(mo-mu)+mu;
nm;(x-xu)/(xo-xu)*(no-nu)+nu;
nn;(y-yu)/(yo-yu)*(nm-mm)+mm;
nn))
LAMBDA: Die WENNFEHLER-Anweisungen sorgen wieder - wie bei der eindimensionalen Interpolation - dafür, dass die äußeren Werte auch für Interpolationen außerhalb der Interpolationsgrenzen gelten. Bei der VBA-Lösung habe ich dies nicht vorgesehen; dort ergibt sich dann ein Fehler. Kann man aber nachrüsten.
Zweidimensionale Interpolation mit INDEX ohne LET/LAMBDA auch für älteres Excel!
A1: X-Suchwert
B1:C5: X-Werte und Y-Werte (als nebeneinanderliegende Spalten; sonst halt MTRANS mit verwenden)
=LINEAREINTERPOLATION(A1;B1:C5) mit LINEAREINTERPOLATION benennend
=LAMBDA(z;xy;LET(x;INDEX(xy;;1);y;INDEX(xy;;2);c;VERGLEICH(z;x);d;c+1;
(INDEX(y;d)-INDEX(y;c))*(z-INDEX(x;c))/(INDEX(x;d)-INDEX(x;c))+INDEX(y;c)))
Achtung: Die X-Werte müssen aufsteigen. Außerhalb der beiden äußersten Werte gibt es Fehler. Möchte man diese Fehler durch Interpolationsweiterführung umgehen, dann bitte die fette Zuweisung durch folgende 2 Zuweisungen ersetzen: e;VERGLEICH(z;x);c;WENNFEHLER(e-(ZEILEN(x)=e);1);
=LINEAREINTERPOLATION(0;{1.2;8.7;9.9}) ergibt #NV oder bei o.g. Ersatz 1,28571429
=LINEAREINTERPOLATION(10;{1.2;8.7;9.9}) ergibt #BEZUG! oder bei o.g. Ersatz 11
Dann funktioniert die Interpolation genauso wie TREND mit nur 2 Punkten, nur - anders als dort mit nur einer Gerade - mit mehreren aneinandergereihten Geraden, deren beide äußere dann unendlich lang sind.
Zweidimensionale lineare Interpolation
A1: X-Wert
B1: Y-Wert
C1: Beginn der 2D-Tabelle inklusive Vorspalte y und Kopfzeile x
Geht diese 2D-Tabelle bis J9, ermittelt die nachfolgende Funktion (VBA oder LAMBDA)
die Kopfzeile x zu D1:J1 (Horiz)
die Vorspalte y zu C2:C9 (Verti)
die Suchmatrix zu D2:J9 (Matri).
Ist die Tabelle noch nicht in der beschriebenen Form, muss sie zunächst so hergestellt werden.
Public Function Interpolation2Dim(ByVal B As Range, x, y)
Spaln = B.Columns.Count
Zeiln = B.Rows.Count
Horiz = B.Offset(0, 1).Resize(1, Spaln - 1)
Verti = B.Offset(1, 0).Resize(Zeiln - 1, 1)
Matri = B.Offset(1, 1).Resize(Zeiln - 1, Spaln - 1)
i = Application.Match(y, Verti)
j = Application.Match(x, Horiz)
xu = Horiz(1, j + 0): mu = Matri(i + 0, j + 0)
xo = Horiz(1, j + 1): mo = Matri(i + 0, j + 1)
yu = Verti(i + 0, 1): nu = Matri(i + 1, j + 0)
yo = Verti(i + 1, 1): no = Matri(i + 1, j + 1)
mm = (x - xu) / (xo - xu) * (mo - mu) + mu
nm = (x - xu) / (xo - xu) * (no - nu) + nu
nn = (y - yu) / (yo - yu) * (nm - mm) + mm
Interpolation2Dim = nn
End Function
=LINEAREINTERPOLATION2DIM(A1;B1;C1#) mit LINEAREINTERPOLATION2DIM benennend
=LAMBDA(x;y;z;LET(
Horiz;WEGLASSEN(INDEX(z;1;);;1);
Verti;WEGLASSEN(INDEX(z;;1);1;);
Matri;WEGLASSEN(z;1;1);
ii;VERGLEICH(y;Verti);i;WENNFEHLER(ii-(ZEILEN(Verti)=ii);1);
jj;VERGLEICH(x;Horiz);j;WENNFEHLER(jj-(SPALTEN(Horiz)=jj);1);
xu;INDEX(Horiz;j+0);mu;INDEX(Matri;i+0;j+0);
xo;INDEX(Horiz;j+1);mo;INDEX(Matri;i+0;j+1);
yu;INDEX(Verti;i+0);nu;INDEX(Matri;i+1;j+0);
yo;INDEX(Verti;i+1);no;INDEX(Matri;i+1;j+1);
mm;(x-xu)/(xo-xu)*(mo-mu)+mu;
nm;(x-xu)/(xo-xu)*(no-nu)+nu;
nn;(y-yu)/(yo-yu)*(nm-mm)+mm;
nn))
LAMBDA: Die WENNFEHLER-Anweisungen sorgen wieder - wie bei der eindimensionalen Interpolation - dafür, dass die äußeren Werte auch für Interpolationen außerhalb der Interpolationsgrenzen gelten. Bei der VBA-Lösung habe ich dies nicht vorgesehen; dort ergibt sich dann ein Fehler. Kann man aber nachrüsten.
Zweidimensionale Interpolation mit INDEX ohne LET/LAMBDA auch für älteres Excel!
WIN/MSO schicken angeblich alle 5 Sekunden Deinen Screen heim zu Papa (recall-Klausel).