Mit einer gewöhnlichen Differenzialgleichung anpassen
Fitting-Ordinary-Differential-Equation
Zusammenfassung
In diesem Tutorial erfahren Sie, wie Sie eine gewöhnliche Differenzialgleichung (ODE) in dem Dialog Fitfunktionen erstellen definieren und eine Anpassung der Daten mit dieser Anpassungsfunktion durchführen.
Origin-Version mind. erforderlich: Origin 9.1 SR0
Was Sie lernen werden
Dieses Tutorial zeigt Ihnen, wie Sie:
- eine ODE-Anpassungsfunktion definieren.
- NAG-Funktionen mit Origin C-Code aufrufen.
- das ODE-Ergebnis nur neu berechnen, wenn die Parameter aktualisiert werden.
- für das ODE-Ergebnis eine Interpolation durchführen.
Beispiel und Schritte
In diesem Tutorial wird beispielhaft eine gewöhnliche Differenzialgleichung erster Ordnung verwendet:
![\frac{\mathrm{d} y}{\mathrm{d} x}=ay \frac{\mathrm{d} y}{\mathrm{d} x}=ay](//d2mvzyuse3lwjc.cloudfront.net/doc/de/Tutorial/images/Fitting_with_an_Ordinary_Differential_Equation/math-3139ba5ac00c6da70c79240db577d5af.png)
![y|_{x=x0}=y0 y|_{x=x0}=y0](//d2mvzyuse3lwjc.cloudfront.net/doc/de/Tutorial/images/Fitting_with_an_Ordinary_Differential_Equation/math-fa0aad52f07a3069cc4b0a22552679b3.png)
wobei a ein Parameter in der gewöhnlichen Differenzialgleichung und y0 der Anfangswert für die gewöhnliche Differenzialgleichung (ODE) ist. Die NAG-Funktionen d02pvc und d02pcc werden mit der Runge-Kutta-Methode aufgerufen, um das ODE-Problem zu lösen.
Daten importieren
- Öffnen Sie eine leere Arbeitsmappe. Wählen Sie Hilfe: Ordner öffnen: Sample-Ordner ... im Menü, um den Ordner "Samples" zu öffnen. Öffnen Sie in diesem Ordner den Unterordner Curve Fitting. Dort befindet sich die Datei Exponential Growth.dat. Ziehen Sie diese Datei per Drag&Drop in das leere Arbeitsblatt, um sie zu importieren.
- Markieren Sie Spalte B und wählen Sie Zeichnen: Symbol: Punktdiagramm im Origin-Menü. Das Diagramm sollte folgendermaßen aussehen:
![Fit ODEex.jpg](//d2mvzyuse3lwjc.cloudfront.net/doc/de/Tutorial/images/Fitting_with_an_Ordinary_Differential_Equation/Fit_ODEex.jpg)
Anpassungsfunktion definieren
Die Anpassungsfunktion kann mit Hilfe des Hilfsmittels Fitfunktionen erstellen definiert werden.
- Wählen Sie Hilfsmittel: Fitfunktionen erstellen im Origin-Menü.
- Stellen Sie sicher, dass im Dialog Fitfunktion erstellen auf der Seite Ziel die Option Neue Funktion erstellen aktiviert ist. Klicken Sie auf die Schaltfläche Weiter.
- Wählen Sie auf der Seite Name und Typ in der Auswahlliste Eine Kategorie auswählen oder erstellen die Option Benutzerdefiniert. Geben Sie für Funktionsname den Text FitODE ein. Aktivieren Sie im Abschnitt Funktionstyp die Option Origin C. Klicken Sie auf Weiter.
- Geben Sie auf der Seite Variablen und Parameter die Parameter a, y0 in das Feld Parameter ein. Klicken Sie auf Weiter.
- Klicken Sie auf der Seite Origin C-Anpassungsfunktion auf die Schaltfläche
rechts vom Bearbeitungsfeld Funktionskörper und definieren Sie die Funktion im Code Builder folgendermaßen. Binden Sie Kopfdateien für NAG und Anpassung ein:
#include <oc_nag.h> #include <ONLSF.H>
Definieren Sie eine statische Funktion, um die ODE durch Aufrufen von NAG-Funktionen zu lösen. Rufen Sie die NAG-Funktion d02pvc auf, um das ODE-Modell zu erzeugen, und d02pcc, um das Modell zu lösen.
struct user // parameter in the ODE { double a; }; //Define the differentiate equation: y'=a*y static void NAG_CALL f(double t, Integer neq, const double *y, double *yp, Nag_Comm *comm) { neq; //Number of ordinary differential equations t; //Independent variable y; //Dependent variables yp; //First derivative struct user *sp = (struct user *)(comm->p); double a; a = sp->a; yp[0] = a*y[0]; } //Use Runge-Kutta ODE23 to solve ODE static bool nag_ode_fit( const double a, const double y0, const double tstart, const double tend, const int nout, vector &vP ) { //nout: Number of points to output if( nout < 2 ) return false; vP.SetSize( nout ); vP[0] = y0; int neq = 1; //Number of ordinary differential equations Nag_RK_method method; double hstart, tgot, tinc; double tol, twant; int i, j; vector thres(neq), ygot(neq), ymax(neq), ypgot(neq), ystart(neq); Nag_ErrorAssess errass; Nag_Comm comm; struct user s; s.a = a; comm.p = (Pointer)&s; ystart[0] = y0; for (i=0; i<neq; i++) thres[i] = 1.0e-8; errass = Nag_ErrorAssess_off; hstart = 0; method = Nag_RK_2_3; tinc = (tend-tstart)/(nout-1); tol = 1.0e-3; NagError nagErr1; //Setup ODE int iwsav[130]; double* rwsav = (double*)malloc((350 + 32*neq)*sizeof(double)); nag_ode_ivp_rkts_setup(neq, tstart, tend, ystart, tol, thres, method, errass, hstart, iwsav, rwsav, &nagErr1); if( nagErr1.code != NE_NOERROR ) { free(rwsav); return false; } for (j=1; j<nout; j++) { twant = tstart + j*tinc; NagError nagErr2; //Solve ODE nag_ode_ivp_rkts_range(f, neq, twant, &tgot, ygot, ypgot, ymax, &comm, iwsav, rwsav, &nagErr2); if( nagErr2.code != NE_NOERROR ) { free(rwsav); return false; } vP[j] = ygot[0]; } free(rwsav); return true; }
Definieren Sie den Körper der Fitfunktion _nlsfFitODE:
NLFitContext *pCtxt = Project.GetNLFitContext(); if ( pCtxt ) { static vector vX, vY; static int nSize; BOOL bIsNewParamValues = pCtxt->IsNewParamValues(); // If parameters were updated, we will recalculate the ODE result. if ( bIsNewParamValues ) { //Initial and final values of the independent variable double tstart = 0.02, tend = 2, tinc; int nout = 100; //Number of points tinc = (tend-tstart)/(nout-1); vX.Data( tstart, tend, tinc ); nSize = vX.GetSize(); if( !nag_ode_fit( a, y0, tstart, tend, nout, vY) ) return; } //Interpolate y from fitting data's x on the ODE result. ocmath_interpolate( &x, &y, 1, vX, vY, nSize ); }
Klicken Sie auf die Schaltfläche Kompilieren, um den Funktionskörper zu kompilieren. Um zum Dialog zurückzukehren, klicken Sie auf Zurück zum NSLF. Die Schaltfläche Auswerten im Dialog zeigt die schwarze Figur einer laufenden Person. Wenn Sie auf sie klicken wird der Wert y = 2,6627270424371 gezeigt. Dies impliziert, dass die Funktion funktioniert. Klicken Sie auf Weiter.
- Wählen Sie auf der Seite Parameterinitialisierungscode die Option Benutzerdefinierten Code verwenden und geben Sie den Code in das Feld Initialisierungscode ein:
//Set the start y value in fitting data as the initial value of y0 y0 = y_data[0]; a = 1;
Klicken Sie auf die Schaltfläche Fertigstellen.
Hinweis: Um die angepassten Parameter zu überwachen, wurde die Klasse NLFitContext zum Definieren von Anpassungsfunktionen eingeführt, um einige Schlüsselinformationen innerhalb des Fitters zu erreichen. |
Kurve anpassen
- Markieren Sie Spalte B und wählen Sie Analyse: Anpassen: Nichtlinearer Fit im Origin-Menü. Wählen Sie im Dialog NLFit auf der Seite Einstellungen: Funktionsauswahl die Option User Defined in der Auswahlliste Kategorie und die Funktion FitODE in der Liste Funktion.
- Gehen Sie zur Registerkarte Parameter und legen Sie y0, wie im Dialog gezeigt, fest.
-
![Fit ODE FitP.jpg](//d2mvzyuse3lwjc.cloudfront.net/doc/de/Tutorial/images/Fitting_with_an_Ordinary_Differential_Equation/Fit_ODE_FitP.jpg)
- Klicken Sie auf die Schaltfläche Fit, um die Kurve anzupassen.
Anpassungsergebnisse
Die angepasste Kurve sollte folgendermaßen aussehen:
-
![Fit ODE Curve.png](//d2mvzyuse3lwjc.cloudfront.net/doc/de/Tutorial/images/Fitting_with_an_Ordinary_Differential_Equation/Fit_ODE_Curve.png)
Die angepassten Parameter werden in der folgenden Tabelle gezeigt:
Parameter |
Wert |
Standardfehler |
a |
1,30272 |
0,00858 |
y0 |
0,77038 |
0 |
Hinweis: Die Anpassung mit komplexeren ODE-Anpassungsfunktionen kann auch auf ähnliche Weise durchgeführt werden.
|