Ich habe die findcontours()
Methode verwendet, um die Kontur aus dem Bild zu extrahieren, aber ich habe keine Ahnung, wie man die Krümmung aus einer Reihe von Konturpunkten berechnet. Kann mir jemand helfen? Vielen Dank!Wie kann ich die Krümmung einer extrahierten Kontur durch opencv berechnen?
Antwort
Für mich Krümmung ist:
wo t
die Position innerhalb der Kontur ist und x(t)
resp. y(t)
geben Sie die zugehörigen x
resp. y
Wert. Siehe here.
Also, nach meiner Definition der Krümmung, kann man es auf diese Weise implementieren:
std::vector<float> vecCurvature(vecContourPoints.size());
cv::Point2f posOld, posOlder;
cv::Point2f f1stDerivative, f2ndDerivative;
for (size_t i = 0; i < vecContourPoints.size(); i++)
{
const cv::Point2f& pos = vecContourPoints[i];
if (i == 0){ posOld = posOlder = pos; }
f1stDerivative.x = pos.x - posOld.x;
f1stDerivative.y = pos.y - posOld.y;
f2ndDerivative.x = - pos.x + 2.0f * posOld.x - posOlder.x;
f2ndDerivative.y = - pos.y + 2.0f * posOld.y - posOlder.y;
float curvature2D = 0.0f;
if (std::abs(f2ndDerivative.x) > 10e-4 && std::abs(f2ndDerivative.y) > 10e-4)
{
curvature2D = sqrt(std::abs(
pow(f2ndDerivative.y*f1stDerivative.x - f2ndDerivative.x*f1stDerivative.y, 2.0f)/
pow(f2ndDerivative.x + f2ndDerivative.y, 3.0)));
}
vecCurvature[i] = curvature2D;
posOlder = posOld;
posOld = pos;
}
Es funktioniert auf nicht geschlossene pointlists auch. Bei geschlossenen Konturen möchten Sie möglicherweise das Grenzverhalten ändern (für die ersten Iterationen).
UPDATE:
Erläuterung für die Derivate:
Ein Derivat nach einer kontinuierlichen 1 dimensionalen Funktion f(t)
ist:
aber wir sind in einem diskreten Raum und haben zwei diskrete Funktionen f_x(t)
und f_y(t)
wo die kleinste Stufe für t
ist eins.
Die zweite Ableitung ist die Ableitung der ersten Ableitung:
die Annäherung der ersten Ableitung verwenden, ist es ergibt zu:
Es gibt andere Näherungen für die Derivate, wenn y google es, Sie werden eine Menge finden.
Während die Theorie hinter Gombats Antwort korrekt ist, gibt es sowohl im Code als auch in den Formeln einige Fehler (der Nenner t+n-x
sollte t+n-t
sein).Ich habe einige Änderungen vorgenommen:
- symmetrische Derivate Verwendung präzise Positionen der Krümmungsmaxima zu bekommen
- erlauben eine Schrittgröße für derivative Berechnung zu verwenden (kann verwendet werden, um Rauschen von lauten Konturen zu reduzieren)
- Werke mit geschlossenen Konturen
Fixes: * Rückkehr Unendlichkeit als Krümmung wenn Nenner 0 ist (nicht 0) * hinzugefügt Quadratberechnungs in Nenner * korrekte Überprüfung auf 0 Divisor
std::vector<double> getCurvature(std::vector<cv::Point> const& vecContourPoints, int step)
{
std::vector<double> vecCurvature(vecContourPoints.size());
if (vecContourPoints.size() < step)
return vecCurvature;
auto frontToBack = vecContourPoints.front() - vecContourPoints.back();
std::cout << CONTENT_OF(frontToBack) << std::endl;
bool isClosed = ((int)std::max(std::abs(frontToBack.x), std::abs(frontToBack.y))) <= 1;
cv::Point2f pplus, pminus;
cv::Point2f f1stDerivative, f2ndDerivative;
for (int i = 0; i < vecContourPoints.size(); i++)
{
const cv::Point2f& pos = vecContourPoints[i];
int maxStep = step;
if (!isClosed)
{
maxStep = std::min(std::min(step, i), (int)vecContourPoints.size()-1-i);
if (maxStep == 0)
{
vecCurvature[i] = std::numeric_limits<double>::infinity();
continue;
}
}
int iminus = i-maxStep;
int iplus = i+maxStep;
pminus = vecContourPoints[iminus < 0 ? iminus + vecContourPoints.size() : iminus];
pplus = vecContourPoints[iplus > vecContourPoints.size() ? iplus - vecContourPoints.size() : iplus];
f1stDerivative.x = (pplus.x - pminus.x)/(iplus-iminus);
f1stDerivative.y = (pplus.y - pminus.y)/(iplus-iminus);
f2ndDerivative.x = (pplus.x - 2*pos.x + pminus.x)/((iplus-iminus)/2*(iplus-iminus)/2);
f2ndDerivative.y = (pplus.y - 2*pos.y + pminus.y)/((iplus-iminus)/2*(iplus-iminus)/2);
double curvature2D;
double divisor = f1stDerivative.x*f1stDerivative.x + f1stDerivative.y*f1stDerivative.y;
if (std::abs(divisor) > 10e-8)
{
curvature2D = std::abs(f2ndDerivative.y*f1stDerivative.x - f2ndDerivative.x*f1stDerivative.y)/
pow(divisor, 3.0/2.0) ;
}
else
{
curvature2D = std::numeric_limits<double>::infinity();
}
vecCurvature[i] = curvature2D;
}
return vecCurvature;
}
- 1. OpenCV wie Kontur glätten, Lärm zu reduzieren
- 2. Finden der Länge der Kontur in opencv
- 3. Wie entferne ich eine Kontur innerhalb der Kontur in Python OpenCV?
- 4. OpenCV Kontur Mindestmaß Ort in Python
- 5. OpenCV C++: Konturen nach ihrer Kontur sortierenArea
- 6. Bestimmen, ob eine Farbe innerhalb einer Kontur ist OpenCV
- 7. Berechnen der Fläche eines Objekts mit OpenCV
- 8. Finden Sie eine Linie senkrecht zu einer Kontur
- 9. Suchen, ob eine Kontur innerhalb einer anderen Kontur existiert
- 10. berechnen Abstand (Disparität) OpenCV
- 11. Wie berechnet man die "Krümmung" einer Kurve mit einer Menge von Punkten?
- 12. Python/OpenCV: Berechnen einer Tiefenkarte aus Stereobildern
- 13. Wie kann ich die Varianz einer Liste in Python berechnen?
- 14. Wie importiere ich die extrahierten JSON Daten in die Datenbank
- 15. berechnen automatische Belichtung in openCv
- 16. Gibt es eine Funktion in openCV oder einer anderen Bibliothek, die Quadrate innerhalb einer beliebigen Kontur kacheln kann?
- 17. akka-http: Wie kann ich einen extrahierten Wert konsumieren/verbergen?
- 18. Auto Hyperlink die extrahierten Dateien
- 19. innerhalb einer Kontur in opencv die Anzahl der Kinder Konturen Zählen
- 20. OpenCV: Wie kann man nach Aufruf cvFindContours() auf eine Kontur in O (1) zugreifen?
- 21. Wie schneidet man den inneren Bereich einer Kontur?
- 22. opencv einen Teil des Bildes innerhalb Kontur beschneiden
- 23. Ich versuche mein eigenes Histogramm zu berechnen ohne opencv calcHist()
- 24. R - Wie finde ich Punkte innerhalb einer bestimmten Kontur?
- 25. OpenCV Android - Berechnen Sie den Durchschnitt einer Spalte von Mat
- 26. Wie zeichnet man eine Linie vom Schwerpunkt einer Kontur zum Umfang der Kontur?
- 27. Wie kann ich die nächste positive semi-definite Matrix berechnen?
- 28. Wie kann ich eine große Exponentialfunktion berechnen?
- 29. Was bedeutet len (Kontur)?
- 30. Wie kann ich in OpenCV von einer XML-Zeichenfolge lesen?
Es würde enorm helfen, wenn Sie uns die Liste der Dinge liefern, die Sie bereits versucht haben und mit einer spezifischeren Frage. – YePhIcK