WICHTIG: Der Betrieb von goMatlab.de wird privat finanziert fortgesetzt. - Mehr Infos...

Mein MATLAB Forum - goMatlab.de

Mein MATLAB Forum

 
Gast > Registrieren       Autologin?   

Partner:




Forum
      Option
[Erweitert]
  • Diese Seite per Mail weiterempfehlen
     


Gehe zu:  
Neues Thema eröffnen Neue Antwort erstellen

Berechnung beschleunigen

 

Axel
Forum-Anfänger

Forum-Anfänger


Beiträge: 12
Anmeldedatum: 29.07.11
Wohnort: ---
Version: ---
     Beitrag Verfasst am: 31.10.2012, 17:34     Titel: Berechnung beschleunigen
  Antworten mit Zitat      
Hallo,

ich habe eine Frage zur Geschwindigkeit in Matlab.

Ich führe folgende Funktion sehr oft (rund 10^10 mal) aus und habe festgestellt, dass diese Berechnung die absolute "Bremse" in meinem Gesamtkonzept ist. Habt Ihr eine Idee wie man dieses beschleunigen kann? Die Funktion berechnet den Ausgangsvekor eines Strahl in Abhängigkeit der Brechungsindizes und des Ebenen- sowie Einfallsvektors. Die Reflexion wird berücksichtigt.

Code:

function [s2,ref] = brechung(ev,s1v,n1v,n2v)

global s1 n1 n2 e

% normalenvektor der Oberfläche
e = ev; e =e/norm(e);
% Strahlvektor Eingang
s1 = s1v; s1=s1/norm(s1);
% Brechungsindex vor Oberfläche
n1 = n1v;
% Brechungsindex hinter Oberfläche
n2 = n2v;

% Strahlvektor Ausgang
[s2,Fval,exitflag] = fsolve(@calcBrechung, s1, optimset('Display','off'));

if (exitflag <= 0)
    ref = 1;
    s2 = s1 - (2*s1*e')*e;
    s2 = s2/norm(s2);
else
    ref = 0;
    s2 = s2/norm(s2);
end

end

function F=calcBrechung(x)

global s1 n1 n2 e

F = [ norm(x)-1;
      norm(cross(s1,e))*n1 - norm(cross(x,e))*n2;
      dot(x,cross(s1,e)) ];
end
 


Gruß und Danke
Private Nachricht senden Benutzer-Profile anzeigen


MaFam
Forum-Meister

Forum-Meister


Beiträge: 799
Anmeldedatum: 02.05.12
Wohnort: ---
Version: R2009b
     Beitrag Verfasst am: 01.11.2012, 10:51     Titel:
  Antworten mit Zitat      
Hallo,

die Gleichung dot(x,cross(s1,e))=0 hat unendlich viele Lösungen. Kannst du das einschränken? Dann könnte man vielleicht explizit einen Vektor bestimmen, der senkrecht auf cross(s1,e) steht. Dadurch könnte man zumindest den Aufruf des Solvers umgehen.

Grüße, Marc
Private Nachricht senden Benutzer-Profile anzeigen
 
Jan S
Moderator

Moderator


Beiträge: 11.057
Anmeldedatum: 08.07.10
Wohnort: Heidelberg
Version: 2009a, 2016b
     Beitrag Verfasst am: 02.11.2012, 15:22     Titel: Re: Berechnung beschleunigen
  Antworten mit Zitat      
Hallo Axel,

NORM und CROSS sind nicht effizient in Matlab implementiert. Da calcBrechung sehr oft ausgeführt wird, wäre eine handgeschriebene Version sinnvoll. Also statt "cross(X,Y)" :
Code:
R = [ X(2) .* Y(3) - X(3) .* Y(2), ...
      X(3) .* Y(1) - X(1) .* Y(3), ...
      X(1) .* Y(2) - X(2) .* Y(1)];

usw.

Die Benutzung globaler Variablen für Parameter ist nicht optimal. Dazu benutzt man besser eine anoyme Funktion. Aber ich vermute, dass dies die Laufzeit nicht sonderlich beeinflusst.

Gruß, Jan
Private Nachricht senden Benutzer-Profile anzeigen
 
Axel
Themenstarter

Forum-Anfänger

Forum-Anfänger


Beiträge: 12
Anmeldedatum: 29.07.11
Wohnort: ---
Version: ---
     Beitrag Verfasst am: 05.11.2012, 09:34     Titel:
  Antworten mit Zitat      
Hi,

danke für die Tipps. Ich konnte das Problem wirklich explizieter gestalten.

Code:

function [s2t,refl] = brechung_d(e1,s1,n1,n2)
e1 = e1/norm(e1);
s1 = s1/norm(s1);

rotachse = cross(e1,s1);
rotachse = rotachse/norm(rotachse);
winkel = acos(e1*s1');

%Es findet keine Brechung statt sondern Reflektion
if ((sin(winkel)*n1/n2)<=-1)||((sin(winkel)*n1/n2)>=1)
    s2t = s1 - (2*s1*e1')*e1;
    s2t = s2t/norm(s2t);
    refl = 1;
else %Brechung im 3D Raum
    winkel_out = asin(sin(winkel)*n1/n2);
    s2t = Drehmatrix(winkel_out,rotachse,e1')';
    s2t = s2t/norm(s2t);
    refl = 0;
end

end
 


Die Funktion Drehmatrix ist tut genau das was unter http://de.wikipedia.org/wiki/Drehmatrix Drehung in R^3 beschrieben ist. Durch diese Änderung habe ich eine Verkürzung der Rechenzeit um Faktor 60.

Das expliziete Formulieren des Kreuzproduktes hat leider keine Verbesserung gebracht.

Danke und viele Grüße
Axel
Private Nachricht senden Benutzer-Profile anzeigen
 
Jan S
Moderator

Moderator


Beiträge: 11.057
Anmeldedatum: 08.07.10
Wohnort: Heidelberg
Version: 2009a, 2016b
     Beitrag Verfasst am: 05.11.2012, 22:20     Titel:
  Antworten mit Zitat      
Hallo Axel,

Du berechnest im Worst-Case den Ausdruck "sin(winkel)*n1/n2" drei mal pro iteration. es wäre effizienter, die nur einmal zu machen und in einer temporären Variablen zu speichern.

Die Berechnung eines Winkels durch acos(a*b') ist numerisch instabil. ATAN2 ist besser.
"asin(sin(winkel)*n1/n2)" wirkt nicht sinnvoll, oder? Ein REM oder MOD wäre deutlich schneller.

Gruß, Jan
Private Nachricht senden Benutzer-Profile anzeigen
 
Axel
Themenstarter

Forum-Anfänger

Forum-Anfänger


Beiträge: 12
Anmeldedatum: 29.07.11
Wohnort: ---
Version: ---
     Beitrag Verfasst am: 06.11.2012, 14:07     Titel:
  Antworten mit Zitat      
Hi Jan,

danke für dei Tips. Man sollte vielleicht wirklich erst mal auf dem Papier kürzen bevor man mit Coy und Past die Terme einfügt (asin(sin(x)) und so Smile
Bezüglich des REM und MOD könnte ich aber nicht ganz folgen. Kannst Du da vielleicht noch ein Wort mehr verlieren?

Danke und Gruß Axel
Private Nachricht senden Benutzer-Profile anzeigen
 
MaFam
Forum-Meister

Forum-Meister


Beiträge: 799
Anmeldedatum: 02.05.12
Wohnort: ---
Version: R2009b
     Beitrag Verfasst am: 06.11.2012, 14:13     Titel:
  Antworten mit Zitat      
Hallo,

asin(sin(x))=x kann man vereinfachen, asin(sin(x)*a) indes nicht.

Grüße, Marc
Private Nachricht senden Benutzer-Profile anzeigen
 
Jan S
Moderator

Moderator


Beiträge: 11.057
Anmeldedatum: 08.07.10
Wohnort: Heidelberg
Version: 2009a, 2016b
     Beitrag Verfasst am: 07.11.2012, 03:06     Titel:
  Antworten mit Zitat      
Hallo Marc,

Ja, das stimmt natürlich.

Gruß, Jan
Private Nachricht senden Benutzer-Profile anzeigen
 
Neues Thema eröffnen Neue Antwort erstellen



Einstellungen und Berechtigungen
Beiträge der letzten Zeit anzeigen:

Du kannst Beiträge in dieses Forum schreiben.
Du kannst auf Beiträge in diesem Forum antworten.
Du kannst deine Beiträge in diesem Forum nicht bearbeiten.
Du kannst deine Beiträge in diesem Forum nicht löschen.
Du kannst an Umfragen in diesem Forum nicht mitmachen.
Du kannst Dateien in diesem Forum posten
Du kannst Dateien in diesem Forum herunterladen
.





 Impressum  | Nutzungsbedingungen  | Datenschutz | FAQ | goMatlab RSS Button RSS

Hosted by:


Copyright © 2007 - 2025 goMatlab.de | Dies ist keine offizielle Website der Firma The Mathworks

MATLAB, Simulink, Stateflow, Handle Graphics, Real-Time Workshop, SimBiology, SimHydraulics, SimEvents, and xPC TargetBox are registered trademarks and The MathWorks, the L-shaped membrane logo, and Embedded MATLAB are trademarks of The MathWorks, Inc.