Guten Morgen Liebe Mikrocontrollermitglieder, ich bitte um eure Hilfe. Meine Problem ist folgendes: ich habe eine Datenblatt einer Batterie mit SOC, Temp, Zeit und dementsprechend zugehörige Interne Widerstand der Batterie. Ich möchte untzer Matlab eine DGL herstellen, die mir erlaubt die Innenwiderstand der Batterie zu berechnen asl Funktion von SOC, Temp und Zeit Rin = f(SOC, Tem, t). Könnt ihr mir bitte helfen? Datenblatt beigefügt. Dankeschön im voraus.
:
Bearbeitet durch User
Meinst du mit "DGL" Differentialgleichung? Falls ja, verstehe ich nicht, was du meinst. Wenn ich das mal ignoriere, würde ich dich so verstehen, dass du die Tabellenwerte aus dem Datenblatt gerne interpolieren möchtest, um den Innenwiderstand auch an nicht tabellierten Stellen bestimmen zu können? Falls das so ist, dann empfehle ich dir in MATLAB mal "doc interp3" einzugeben.
Hallo crayse und danlke für deine Rückmeldung. Ja ich meine mit "DGL" Differentialgleichung. Ich möchte einen Bock ("Block-Widerstand für eine Simulation") unter Simulink einbauen, der mir bei Eingabe der Temperatur und SOC den zugehörige Widerstand über die Zeit gibt, wie es in der Tabelle steht, also die Möglichkeit Rin als Rin = f(SOC, Tem, t) darstellen zu können. Habe ich das Problem so ein bisschen besser erklärt? Vielen Dank
Hermann N. schrieb: > also die Möglichkeit Rin als > Rin = f(SOC, Tem, t) darstellen zu können. Und warum sollte das die Lösung einer Dgl. sein?
:
Bearbeitet durch User
Ja, das verstehe ich wie gesagt auch nicht ganz. Wo genau kommt da die Differentialgleichung ins Spiel? Wahrscheinlich verstehe ich auch die Tabelle nicht, vielleicht kannst du mir da nochmal helfen. Aber so wie ich das sehe, ist doch der Innenwiderstand mit der Angabe von SOC, T und t schon voll bestimmt (zumindest für die in der Tabelle angegebenen Werte). Welche DGL müsste da deiner Meinung nach gelöst werden? Meinst du damit vielleicht, dass du den Innenwiderstand dann in der Lösung einer DGL verwenden willst?
Hallo crayse - Joel G, Vielleicht habe ich der falsche Ausdruck gemacht. Aber klar möchte ich gern Rin als Rin=f(SOC, Temp, t) in einer Gleichung zusammen definieren, so dass ich Rin bei bestimmten SOC und Temperatur über die Zeit bestimmen kann. Also bei Sumlink einen Block bauen mit SOC, Temp und Zeit als Eingangsparameter und Rin als Output. Habe ich ein bisschen besser klar gemacht? VG
@ S. E. > Meinst du damit vielleicht, dass du den Innenwiderstand dann in der > Lösung einer DGL verwenden willst? Ja das habe ich das so gesehen, diese DGL würde ich dann nutzen um Rin als Output zu bestimmen, wenn SOC, Temp und Zeit t als Input des Blockes verwenden wurden. VG
Hä? Ich glaube wir reden immernoch aneinander vorbei. Wenn du wirklich eine DGL lösen willst, wäre es wohl am einfachsten, wenn du diese mal explizit hinschreibst, vielleicht kann ich dir dann besser helfen, ... In der müssen ja irgendwelche Ableitungen (wahrscheinlich nach der Zeit) vorkommen? Unabhängig davon suchst du ja anscheinend nach einer Implementierung der Funktion f(SOC,T,t), oder? Soll diese so sein, dass sie z.B. folgende Werte zurückgibt: f(SOC=10%,T=25°C,t=2s)=1,43 mOhm oder auch: f(SOC=40%,T=-30°C,t=10s)=15,8 mOhm Falls ja, kannst du das wiegesagt mit interp3 machen. Natürlich nur für Werte die im Wertebereich der Tabelle liegen bzw. zwischen diesen. Für eine Extrapolation außerhalb des Bereichs wirds deutlich komplizierter ...
Hallo Crayse, ich konnte dank dir und deinen Tipps mein obiges Problem lösen. Nun brauche ich bitte wieder deine Hilfe,falls du mir noch gern helfen würde. Es soll folgende Gleichung für die Bestimmung der maximalen bzw. minimalen zugelassenen Lade- Entladestrom einer Lithium-ion Zelle gelöst werden.
also I_Batt ist gesucht. OCV ist der Leerlaufspannung (Open Circuit Voltage) und ist von SOC (State of charge [0 bis 1 in Prozent] wobei 0=0% und 1=100%) abhängig. Rin ist der Innenwiderstand und ist auch von SOC abhängig. detla_E ist ide Änderung der Spannung in Bezug auf die Temperatur und wir durch einem Polynom der Forme
bestimmt (die Gleichung oder das Polynom habe ich auch schon unter Matlab implementiert) . Ich möchte also für SOC =0:0.1:1 den jeweiligen zugehörigen maximal Strom mit dem Newton Verfahren bestimmen (approxmieren), und die Werte von OCV und R_in werden aus einem lookup Table dementsprechend SOC=0:0.1:1 abgelesen. Hast du oder jemand bitte eine Idee wie ich anfangen oder das implementieren kann? Für SOC=0 dann (OCV und R_in aus lookup Tables) für T= 25°C z.B. dann DeltaE(T) aus Polynom
I_Batt durch Newton-Verfahren bestimmen, wenn I_Batt für SOC= 0 gefunden ist dann nächste SOC=0.1 uws. Ein einfaches Newton-Verfahren Implementierung ist gar kein Problem. Vielen Dank im Voraus.
Hermann N. schrieb: > Es soll folgende Gleichung für die Bestimmung der maximalen bzw. > minimalen zugelassenen Lade- Entladestrom einer Lithium-ion Zelle gelöst > werden. Mh, ich muss nochmal nachhaken. Du schreibst nicht, was du für
einsetzt. Ich vermute mal einen festen Wert unter den die Zellenspannung nicht sinken soll. Wenn das wirklich ein fester Wert ist, kannst du die Gleichung doch einfach nach
auflösen, oder? Also:
Wenn du da dann einfach die Werte für einen festen SOC einsetzt müsstest du doch direkt aufs Ergebnis kommen oder nicht? Falls es komplizierter wird, kann man natürlich die Gleichung auch durch Nullstellensuche lösen. Matlab hat da wie immer schon Sachen eingebaut (etwa die Routine fzero). Selbst implementieren macht da imho keinen großen Sinn.
Wir haben das damals in der Uni auch sowas mit Matlab gemacht. Wenn du DGLs mit mehr als einer Ableitung lösen möchtest, so musst du das System erst in Zustandsgleichungen überführen. Dann kannst du das mit einem finite Differenzenverfahren lösen. Die Begriffe sollten einigermaßen Google-bar sein. Es ich das eben schnell und übersichtlich machen wollen würde und mir auch Simulink zur Verfügung steht, würde ich das eben schnell zusammenklicken. Empfehlen kann ich auch Open-Modelica und VHDL-AMS. Dafür gibt es entsprechend viel Freeware, und die Einarbeitungszeit ist meiner Meinung nach etwas geringer als für Matlab.
S. E. schrieb: Guten Morgen Cayse, > Du schreibst nicht, was du für >
einsetzt. Ich vermute mal einen festen Wert > unter den die Zellenspannung nicht sinken soll. ja genau es ist die absolute minimale Spannung (Grenzspannung) und ist bzw. muss ein fester Wert sein (ich habe in meinem Beispiel z.B. den Wert 2.5 eingesezt) > Wenn das wirklich ein > fester Wert ist, kannst du die Gleichung doch einfach nach >
auflösen, oder? > Also: >
> Wenn du da dann einfach die Werte für einen festen SOC einsetzt müsstest > du doch direkt aufs Ergebnis kommen oder nicht? ich habe das auch so versucht > Falls es komplizierter wird, kann man natürlich die Gleichung auch durch > Nullstellensuche lösen. da habe ich mit dem folgenden kleinen Programm versucht, ist aber nur für ein fester SOC. Ich würde gern für SOC=0:0.1:1, da eigentlich der OCV und Rin beide SOC abhängig sind. und da kommt noch dazu die delta_E, was Temperatur abhängig ist (hier habe ich den Wert für 25°C benutzt) clc; clear all; close all; %%%%%%%%%%%% Test Newtonsches Iterationsverfahren %%%%%%%%%%%% format long OCV=3.64; % Open Circuit Voltage %% Rin=2.14e-3; % Innenwiderstand %% für SOC=30%, also 0.3 delta_E= -0.3722; % Änderung der Spannung mit der Temperatur für 25°C U_Grenz_Min=2.5; % fester Wert für U_Grenz_Min I_Batt = 0; % Startwert ab=1; tol=5*1.0e-3; % 1. Abbruch-Wert und Abbruch-Toleranz Imax=200; I=1; % max. Iterationen, 1. Iter.-Schritt while abs(ab) > tol && I < Imax I_Batt0=I_Batt; % Datensicherung I_Batt =I_Batt0 -(OCV - Rin*I_Batt - U_Grenz_Min + delta_E )/(-Rin) ab=I_Batt-I_Batt0; I=I+1; % Lösungsänderung, Iter.-Schritte end
Johannes S. schrieb: Guten Morgen Johannes, > Wir haben das damals in der Uni auch sowas mit Matlab gemacht. Wenn du > DGLs mit mehr als einer Ableitung lösen möchtest, so musst du das System > erst in Zustandsgleichungen überführen. Dann kannst du das mit einem > finite Differenzenverfahren lösen. Die Begriffe sollten einigermaßen > Google-bar sein. > > Es ich das eben schnell und übersichtlich machen wollen würde und mir > auch Simulink zur Verfügung steht, würde ich das eben schnell > zusammenklicken. > > Empfehlen kann ich auch Open-Modelica und VHDL-AMS. Dafür gibt es > entsprechend viel Freeware, und die Einarbeitungszeit ist meiner Meinung > nach etwas geringer als für Matlab. danke für deine Rückmeldung, ich werde mir mal deinen Vorschlag angucken. Vielen Dank
Hermann N. schrieb: >> Wenn du da dann einfach die Werte für einen festen SOC einsetzt müsstest >> du doch direkt aufs Ergebnis kommen oder nicht? > > ich habe das auch so versucht Und was genau hat daran nicht funktioniert? Warum sollte man numerisch nach Nullstellen suchen, wenn man die Gleichung analytisch auflösen kann? Das verstehe ich nicht. Ich denke du kannst einfach folgendes verwenden: OCV=3.64; % Open Circuit Voltage %% Rin=2.14e-3; % Innenwiderstand %% für SOC=30%, also 0.3 delta_E= -0.3722; % Änderung der Spannung mit der Temperatur für 25°C U_Grenz_Min=2.5; % fester Wert für U_Grenz_Min I_Batt=(OCV-U_Grenz_Min+delta_E)/Rin Fertig! Wenn ich damit falsch liegen sollte, dann schreib doch mal, warum das in deinen Augen nicht geht. Oder ist dein eigentliches Problem, das jetzt nicht nur für einen festen Wert sondern für verschiedene Werte von SOC auszurechnen? In diesem Fall könnte man z.B. Funktionen Rin, delta_E und OCV machen, die in Abhängigkeit von SOC (und evtl. T) die passenden Werte zurückgeben und dann sowas wie numT=10; Tvec=linspace(10,40,numT); numSOC=10; SOCvec=linspace(0,1,numSOC); for iT=1:numT for iSOC=1:numSOC I_Batt=OCV(SOCvec(iSOC),Tvec(iT))-U_Grenz_Min+delta_E(SOCvec(iSOC),Tvec( iT)))/Rin(SOCvec(iSOC),Tvec(iT)) end end mit passenden Funktionen OCV(SOC,T),delta_E(SOC,T) und Rin(SOC,T) ... So wie ich das bis jetzt sehe, hat das alles (noch?) gar nichts mit DGLs zu tun, oder?
S. E. schrieb: > So wie ich das bis jetzt sehe, hat das alles (noch?) gar nichts mit DGLs > zu tun, oder? Ja genau mit DGLs hat das ganze nichts mehr zu tun, darauf bin ich auch gar nicht mehr zurückgekommen. Ich probiere jetzt erstmal deinen Vorschlag und danach gebe ich dir ne Rückmeldung. Vielen Dank nochmal für deine Hilfe VG
Wenn du die Werte, wie oben in der Tabelle zu sehen, schon gegeben hast, dann kannst du diese doch einfach in eine Matrix eintragen und in Simulink mithilfe des lookuptable Blocks zu deinen Eingangswerten den entsprechenden Ausgang bekommen!? Warum so kompliziert? Zwischen den verschiedenen Werten kannst du ja auch noch interpolieren wenn du das gerne möchtest.
S. E. schrieb: Hallo Crayse, > Oder ist dein eigentliches Problem, das jetzt nicht nur für einen festen > Wert sondern für verschiedene Werte von SOC auszurechnen? > In diesem Fall könnte man z.B. Funktionen Rin, delta_E und OCV machen, > die in Abhängigkeit von SOC (und evtl. T) die passenden Werte > zurückgeben und dann sowas wie > > numT=10; > Tvec=linspace(10,40,numT); > numSOC=10; > SOCvec=linspace(0,1,numSOC); > > for iT=1:numT > for iSOC=1:numSOC > I_Batt=OCV(SOCvec(iSOC),Tvec(iT))-U_Grenz_Min+delta_E(SOCvec(iSOC),Tvec( iT)))/Rin(SOCvec(iSOC),Tvec(iT)) > > end > end > > mit passenden Funktionen OCV(SOC,T),delta_E(SOC,T) und Rin(SOC,T) ... ich habe mit folgendem Beispiel versucht die OCV zu berechnen, und ich bekomme folgende Fehlermeldung: Error using ==>mpower, Matrix must be square. Kannst du mir bitte sagen, was nun nicht stimmt? numSOC=10; SOCvec=linspace(0,1,numSOC); for iSOCvec=1:numSOC OCV = -1.1465.*(SOCvec)^4 +3.1013.*(SOCvec)^3 -2.3857.*(SOCvec)^2 +1.1115.*(SOCvec) +3.4042 end
:
Bearbeitet durch User
Du hast noch nicht oft MATLAB benutzt, oder? Wenn du die elementweise Potenz von Vektoren nehmen willst, musst du .^ statt ^ verwenden. In deinem Fall, brauchst du dann auch gar keine for-Schleife. Probiers mal hiermit: numSOC=10; SOCvec=linspace(0,1,numSOC); OCV = -1.1465.*(SOCvec).^4 +3.1013.*(SOCvec).^3 -2.3857.*(SOCvec).^2 +1.1115.*(SOCvec) +3.4042
S. E. schrieb: > Du hast noch nicht oft MATLAB benutzt, oder? > Wenn du die elementweise Potenz von Vektoren nehmen willst, musst du .^ > statt ^ verwenden. In deinem Fall, brauchst du dann auch gar keine > for-Schleife. > Probiers mal hiermit: > > numSOC=10; > SOCvec=linspace(0,1,numSOC); > OCV = -1.1465.*(SOCvec).^4 +3.1013.*(SOCvec).^3 -2.3857.*(SOCvec).^2 > +1.1115.*(SOCvec) +3.4042 Du hast recht Matlab habe ich leider nur seit kurzem angefangen. Wenn ich dann keine for-Schleife brauche, wie werde ich dann die verschiedenen Werte für den Strom berechnen, wie du oben schon ein bisschen erklärt hast? >Oder ist dein eigentliches Problem, das jetzt nicht nur für einen festen >Wert sondern für verschiedene Werte von SOC auszurechnen? >In diesem Fall könnte man z.B. Funktionen Rin, delta_E und OCV machen, >die in Abhängigkeit von SOC (und evtl. T) die passenden Werte >zurückgeben und dann sowas wie >numT=10; >Tvec=linspace(10,40,numT); >numSOC=10; >SOCvec=linspace(0,1,numSOC); >for iT=1:numT > for iSOC=1:numSOC > I_Batt=OCV(SOCvec(iSOC),Tvec(iT))-U_Grenz_Min+delta_E(SOCvec>(iSOC),Tvec ( >iT)))/Rin(SOCvec(iSOC),Tvec(iT)) > end >end >mit passenden Funktionen OCV(SOC,T),delta_E(SOC,T) und Rin(SOC,T) ... Deine Beispile würde mir nur zur Berechnung der OCV als f(SOC) dienen oder?
S. E. schrieb: > Du hast noch nicht oft MATLAB benutzt, oder? > Wenn du die elementweise Potenz von Vektoren nehmen willst, musst du .^ > statt ^ verwenden. In deinem Fall, brauchst du dann auch gar keine > for-Schleife. > Probiers mal hiermit: > > numSOC=10; > SOCvec=linspace(0,1,numSOC); > OCV = -1.1465.*(SOCvec).^4 +3.1013.*(SOCvec).^3 -2.3857.*(SOCvec).^2 > +1.1115.*(SOCvec) +3.4042 Folgendes habe ich probiert, ich bekomme aber immer nur einen Wert für den Strom. Kannst du mir mal bitte wo der Fehler liegt? Danke und VG, clc; clear all; close all; %%%%%%%%%%%% Newtonsches Iterationsverfahren zur Berechnung des maximalen Stroms %%%%%%%%%%%% delta_E= -0.3722; % Änderung der Spannung mit der Temperatur, hier für 25°C %% U_Grenz_Min=2.5; % fester Wert für U_Grenz_Min numSOC=20; SOC=linspace(0,1,numSOC); %OCV = -1.1465.*(SOC).^4 +3.1013.*(SOC).^3 -2.3857.*(SOC).^2 +1.1115.*(SOC) +3.4042; %Rin = -5.5186e-3.*(SOC).^4 +10.3749e-3.*(SOC).^3 -5.5877e-3.*(SOC).^2 +0.6510e-3.*(SOC) +1.8168e-3; I_Batt = 0; % Startwert ab=1; tol=5*1.0e-3; % 1. Abbruch-Wert und Abbruch-Toleranz imax=100; i=1; % max. Iterationen, 1. Iter.-Schritt for iSOC=0:numSOC OCV = -1.1465.*(iSOC).^4 +3.1013.*(iSOC).^3 -2.3857.*(iSOC).^2 +1.1115.*(iSOC) +3.4042; Rin = -5.5186e-3.*(iSOC).^4 +10.3749e-3.*(iSOC).^3 -5.5877e-3.*(iSOC).^2 +0.6510e-3.*(iSOC) +1.8168e-3; while abs(ab) > tol && i < imax I_Batt0=I_Batt; % Datensicherung I_Batt =I_Batt0 -(OCV - Rin*I_Batt - U_Grenz_Min + delta_E )/(-Rin) ab=I_Batt-I_Batt0; i=i+1; % Lösungsänderung, Iter.-Schritte end end I_Batt
S. E. schrieb: > numSOC=10; > SOCvec=linspace(0,1,numSOC); > OCV = -1.1465.*(SOCvec).^4 +3.1013.*(SOCvec).^3 -2.3857.*(SOCvec).^2 > +1.1115.*(SOCvec) +3.4042 Ja, dieses Beispiel berechnet tatsächlich nur OCV als Vektor für die entsprechenden Werte von SOC. Aber nur, weil du genau dieses Beispiel oben aufgebracht hast. Du kannst auch alles direkt mit Vektoren (bzw. Matrizen, wenn du die beiden Parameter T und SOC) hast rechnen. Der Übersichtlichkeit halber und weil du dich ja anscheinend noch nicht so gut mit MATLAB auskennst, würde ich dir davon eher abraten. Ich kann nur nochmal meinen Rat von oben wiederholen und folgenden Codeschnippsel anbieten: numT=10; Tvec=linspace(10,40,numT); numSOC=10; SOCvec=linspace(0,1,numSOC); for iT=1:numT for iSOC=1:numSOC I_Batt=OCV(SOCvec(iSOC),Tvec(iT))-U_Grenz_Min+delta_E(SOCvec(iSOC),Tvec( iT)))/Rin(SOCvec(iSOC),Tvec(iT)) end end Das einzige, was für dich jetzt noch zu tun bleibt ist FUNKTIONEN zu definieren, die OCV, Rin und delta_E berechnen. Nachdem du jetzt mit dem Code für die Berechnung von OCV rausgerückt hast, kann ich dir dann sogar schonmal ein Beispiel geben, wie das aussehen könnte: Erstell im gleichen Ordner wie dein Skript eine Datei namens OCV.m in der das folgende steht: function ret = OCV(SOC,T) ret = -1.1465*SOC^4 +3.1013*SOC^3 -2.3857*SOC^2+1.1115*SOC +3.4042 Fertig! Wenn du jetzt in der MATLAB Konsole OCV(0.,0.) eingibst, müsstest du den entsprechenden Wert für OCV bei SOC=0. bekommen. Keine Vektoren, keine Matrizen, einfach nur Zahlen, also alles ganz easy. Hier kannst du jetzt wenn du willst noch die Temperaturabhängigkeit einbauen. Das gleiche (also zwei weitere Dateien mit entsprechenden Funktionen und Dateinamen) machst du jetzt noch für Rin und für delta_E. Wenn du das hast, kannst du obigen Code einfach direkt laufen lassen. Sollte dir dann I_Batt für alle Werte ausgeben. Wenn du willst, kannst du die Ausgabe auch noch etwas verschönern (doc disp). Kannst dich natürlich auch beratungsresistent zeigen und auf dem Newton Iterationsding beharren. Hab aber ehrlich gesagt keine Lust, da irgendwas für dich zu debuggen, weil ichs wie schon erwähnt hier vollkommen sinnlos finde.
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.