ich arbeite an einer Robotersimulation auf Basis einer Intervallanalyse (Verwendung der Toolbox INTLAB) und muss daher die DETERMINANTE einer 6x6 (Jacobi-)Matrix bestimmen (und zwar ziemlich! oft).
Leider kann die Standardfunktion det(x) nicht auf die Intervallmatrizen angewendet werden und die Toolbox INTLAB enthält noch keine solche Routine.
Ich habe von einem Kollegen folgenden Code bekommen, der auf der Leibnizformel/dem Laplace'schen Entwicklungssatz basiert. Die Funktion berechnet zwar korrekte Ergebnisse (was schonmal cool ist) braucht allerdings EWIG.
Da ich noch wenig Erfahrungen in der Programmierung, und gerade in Matlab habe, bitte ich um Tipps zur Rechenzeitoptimierung des folgenden Codes:
function deter = intdet(MAT,minormax) %, pre, secondpre)
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%This programs calculates determinants for interval matrices
%and tries to do in a resonably sharp way
%Input:
% MAT Interval Matrix (Size NxN) (Works slow for N>6) % minormax ('min' / 'max') -> Expand by the smallest/biggest column/row
%Output:
% deter Determinant
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
deter = subintdet(A, minormax); %Calculate the determinant recursive method
end end
function subdet = subintdet(A,minormax) %Subdeterminant
s = size(A,1); %number of rows
if(isequal(size(A), [1,1])) %The recursitivity end when the inputis a 1x1 matrix
subdet = A(1,1);
else
%Recursive algorithm
l = zeros(s,1);
%Find the sums of the diameter of the columns and the rows and store it in l
for i = 1:s,
l(i) = sum(diam(A(i,:))); %rows
l(i+s) = sum(diam(A(:,i))); %columns
end ifstrcmp(minormax, 'min')
mi = min(l); %Expand by the smallest column/row
elseifstrcmp(minormax, 'max')
mi = max(l); %Expand by the biggest column/row
else error('Wrong input to intdet');
end
i=1;
while(l(i) ~= mi), %Find the index of the smallest/biggest row (can be done easier, i know!)
i=i+1;
end
subdet = 0;
for j = 1:s;
U = A;
if(i<=s) %Calculate subdeterminant by the row
U(i,:) = []; %Clear the other rows and columns.
U(:,j) = [];
sig = mod(i+j,2); %Set the sign.
subdet = subdet+((-1)^sig)*A(i,j)*subintdet(U,minormax); %The next subdeterminant is calculated
else %Calculate subdeterminant by the column
r = i-s;
U(:,r) = [];
U(j,:) = [];
sig = mod(r+j,2);
subdet = subdet+((-1)^sig)*A(j,r) * subintdet(U,minormax);
end end end end
Soll bedeuten, dass jedes Matrixelement als ein Intervall [a,b] definiert ist (vgl. Intervallarithmetik zB Wikipedia). Die Toolbox INTLAB stellt weitestgehend alle Rechenoperationen bereit, nur leider nicht für die Determinantenberechnung (Habe der Entwickler Prof. Rump von der TU Hamburg persönlich hierzu befragt). Anscheinend ist noch keine Routine fertiggestellt die Ihren Ansprüchen für eine Implementierung in die Toolbox genügt.
Daher mussten wir halt selbst ran und die gängigen Berechnungsroutine zur Determinantenbestimmung auf Basis der "erlaubten" Rechenoperationen für Intervalle umsetzen.
Wer also evtl noch irgendwo potential hinsichtlich zeit und rechen effizienz sieht, würde mir sehr weiterhelfen.
Danke
Schwer zu sagen, keine Fehlermeldungen, soweit ich feststellen konnte richtige ergebnisse aber die berechnung einer 6x6 Matrix mit moderaten Intervallgerenzen zB +/- 10 duert die Operation gerne über ne Sekunde, was sich aber bei mehreren zehn- bis hunderttausend nötigen berechnungen ganz gut summiert
Schon klar, dass sich das aufsummiert, aber der MATLAB Profiler (über Menü oder per Befehl) zeigt auf, wo die meiste Zeit verbraten wird. Wenn man das weiss kann man versuchen diesen Teil des Codes schneller zu machen.
Das problem ist für mich selbst auch schwer zu durchschauen, da sich die Funktion subdet ja mehrfach selbst aufrufen muss um die Unterdeterminanten zu bilden
Zeile:
subdet = subdet+((-1)^sig)*A(i,j)*subintdet(U,minormax); %The next subdeterminant is calculated
und an der stelle geht natürlich auch die meiste rechenzeit drauf, das bestätigt auch der profiler.
Ich glaube allerdings nicht, dass sich dies an der stelle vermeiden lässt.
Gast
Beiträge: ---
Anmeldedatum: ---
Wohnort: ---
Version: ---
Verfasst am: 18.12.2008, 11:52
Titel:
Kannst Du denn mal eine kleines Beispiel geben, wie z.B. der genaue Rechnungsgang für eine Matrix A=[a b;c d] und meinetwegen den Intervallgrenzen +-10 auszusehen hat?
Oder wie genau sieht denn eine Intervallmatrix aus?
Die ganze Thematik ist mir nämlich völlig fremd...
function deter = intdet_test%(MAT,minormax) %, pre, secondpre)
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%This programs calculates determinants for interval matrices
%and tries to do in a resonably sharp way
%Input:
% MAT Interval Matrix (Size NxN) (Works slow for N>6)
%Output:
% deter Determinant
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
else %no elements are NaN
A = MAT;
profile on
deter = subintdet(A, minormax); %Calculate the determinant recursive method
profile viewer
end end
function subdet = subintdet(A,minormax) %Subdeterminant
s = size(A,1); %number of rows
if(isequal(size(A), [1,1])) %The recursitivity end when the inputis a 1x1 matrix
subdet = A(1,1);
else
%Recursive algorithm
l = zeros(s,1);
%Find the sums of the diameter of the columns and the rows and store it in l
for i = 1:s,
l(i) = sum(diam(A(i,:))); %rows
l(i+s) = sum(diam(A(:,i))); %columns
end ifstrcmp(minormax, 'min')
mi = min(l); %Expand by the smallest column/row
elseifstrcmp(minormax, 'max')
mi = max(l); %Expand by the biggest column/row
else error('Wrong input to intdet');
end
i=1;
while(l(i) ~= mi), %Find the index of the smallest/biggest row (can be done easier, i know!)
i=i+1;
end
subdet = 0;
for j = 1:s;
U = A;
if(i<=s) %Calculate subdeterminant by the row
U(i,:) = []; %Clear the other rows and columns.
U(:,j) = [];
sig = mod(i+j,2); %Set the sign.
subdet = subdet+((-1)^sig)*A(i,j)*subintdet(U,minormax); %The next subdeterminant is calculated
else %Calculate subdeterminant by the column
r = i-s;
U(:,r) = [];
U(j,:) = [];
sig = mod(r+j,2);
subdet = subdet+((-1)^sig)*A(j,r) * subintdet(U,minormax);
end end end end
hey kein problem, aber ich hab heute leider keine zeit mehr, es gibt so nette verpflichtungen wie institutsweihnachtsfeiern;) ich poste morgen vormittag was!
. Leicht für eine 2x2 Matrix.
Jetzt muss ich mal eine 4x4 Matrix durchrödeln, um zu verstehen, welchen der Einträge man nehmen muss und wie dabei die alternierenden Vorzeichen beim Entwicklungssatz zu berücksichtigen sind.
Ich möchte eigentlich aus der Intervallmatrix zwei 'normale' Matrizen machen, daraus dann für die untere und obere Grenze wieder zwei einzelne Matrizen machen (mit jeweils den richtigen Elementen) und darauf dann das det von Matlab loslassen.
Einstellungen und Berechtigungen
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
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.