2010-02-16 10 views
8

Nach Hartley/Zisserman Multiview Geometery, Algorithmus 12: Die optimale Triangulationsmethode (p318), ich habe die entsprechenden Bildpunkte xhat1 und xhat2 (Schritt 10). In Schritt 11 muss der 3D-Punkt Xhat berechnet werden. Eine solche Methode ist die direkte lineare Transformation (DLT), die in 12.2 (p312) und 4.1 (p88) erwähnt wird.Triangulation & Direkte lineare Transformation

Die homogene Methode (DLT), p312-313, heißt es, dass es eine Lösung, wie die Einheit singuläre Vektor findet den kleinsten Singulärwert von A entspricht, also

A = [xhat1(1) * P1(3,:)' - P1(1,:)' ; 
     xhat1(2) * P1(3,:)' - P1(2,:)' ; 
     xhat2(1) * P2(3,:)' - P2(1,:)' ; 
     xhat2(2) * P2(3,:)' - P2(2,:)' ]; 

[Ua Ea Va] = svd(A); 
Xhat = Va(:,end); 

plot3(Xhat(1),Xhat(2),Xhat(3), 'r.'); 

jedoch A ein 16x1 Matrix, was zu einem Va führt, das 1x1 ist.

Was mache ich falsch (und eine Lösung), um den 3D-Punkt zu bekommen?

Für das, was ihren Wert Beispieldaten:

xhat1 = 

    1.0e+009 * 

    4.9973 
    -0.2024 
    0.0027 


xhat2 = 

    1.0e+011 * 

    2.0729 
    2.6624 
    0.0098 


P1 = 

    699.6674   0 392.1170   0 
     0 701.6136 304.0275   0 
     0   0 1.0000   0 


P2 = 

    1.0e+003 * 

    -0.7845 0.0508 -0.1592 1.8619 
    -0.1379 0.7338 0.1649 0.6825 
    -0.0006 0.0001 0.0008 0.0010 


A = <- my computation 

    1.0e+011 * 

    -0.0000 
     0 
    0.0500 
     0 
     0 
    -0.0000 
    -0.0020 
     0 
    -1.3369 
    0.2563 
    1.5634 
    2.0729 
    -1.7170 
    0.3292 
    2.0079 
    2.6624 

aktualisieren für Abschnitt xi Arbeits Code in Algorithmus

% xi 
A = [xhat1(1) * P1(3,:) - P1(1,:) ; 
    xhat1(2) * P1(3,:) - P1(2,:) ; 
    xhat2(1) * P2(3,:) - P2(1,:) ; 
    xhat2(2) * P2(3,:) - P2(2,:) ]; 

A(1,:) = A(1,:)/norm(A(1,:)); 
A(2,:) = A(2,:)/norm(A(2,:)); 
A(3,:) = A(3,:)/norm(A(3,:)); 
A(4,:) = A(4,:)/norm(A(4,:)); 

[Ua Ea Va] = svd(A); 
X = Va(:,end); 
X = X/X(4); % 3D Point 
+0

Es wäre besser, mit den kleinsten erwarteten Eingaben schreiben für xhat1, P1 usw., sodass wir ein funktionierendes Beispiel kopieren und einfügen können und nicht davon ausgehen müssen, in welcher Form Ihre Eingaben sind. – MatlabDoug

Antwort

10

Wie im Buch erwähnt wird (s 12.2), pi T sind die Zeilen von P. Daher müssen Sie P1(k,:) nicht transponieren (d. H. Die richtige Formulierung ist A = [xhat1(1) * P1(3,:) - P1(1,:) ; ...).

Ich hoffe, das war nur ein Tippfehler.

Zusätzlich wird empfohlen, jede Zeile von A mit seiner L2-Norm zu normalisieren, dh für alle i

A(i,:) = A(i,:)/norm(A(i,:));

Und wenn man die triangulierten 3D-Punkte zeichnen möchten, müssen Sie Xhat normalisieren vor (seine sinnlose sonst) Plotten, dh

Xhat = Xhat/Xhat(4);

+0

Jacob, Sie erwähnen, dass die Zeilen von A normalisiert werden sollten. Ist die Frobenius-Norm (?) Sehr verschieden von der Normalisierung auf p109, die xhat1 und xhat2 normalisiert, die DLT dann normalisiert? – yxk

+1

Nein, es ist anders - es wird nur verwendet, um die SVD-Berechnung das Kosinus-Maß verwenden zu lassen. Und ich meinte die L2-Norm, also || A (i, :) ||. – Jacob

+0

In meinem Fall führte die Normalisierung von A-Zeilen vor der SVD-Anwendung zu unvorhersehbaren Reprojektionsfehlern (berechnet durch Projizieren des triangulierten Punkts auf die Kameras und Berechnen des Abstands zwischen den Projektionen und den Eingaben für die Triangulation) im Bereich von 0,007 bis 22 Pixel. Durch das Entfernen der Normalisierung wurde der Bereich auf 0,001-0,4 Pixel erhöht. – neuviemeporte