7 Stimmen

Sind GPUs gut für fallbasierte Bildfilterung?

Ich versuche herauszufinden, ob ein bestimmtes Problem ein guter Kandidat für die Verwendung von CUDA ist, um das Problem auf einen Grafikprozessor zu übertragen.

Ich tue im Wesentlichen eine Box-Filter, die auf einige Kante Erkennung basiert ändert. So gibt es im Grunde 8 Fälle, die für jedes Pixel getestet werden, und dann der Rest der Operationen passieren - typische mittlere Berechnungen und so. Ist das Vorhandensein dieser switch-Anweisungen in meiner Schleife gehen, um dieses Problem ein schlechter Kandidat zu gehen, um GPU verursachen?

Ich bin mir nicht sicher, wie man die Switch-Anweisungen vermeiden kann, da die Kantenerkennung bei jedem Pixel erfolgen muss. Ich nehme an, das gesamte Bild könnte die Kantenerkennung Teil aus der Verarbeitung Algorithmus aufgeteilt haben, und Sie könnten einen Puffer entsprechend, welche Filter für jedes Pixel zu verwenden speichern, aber das scheint, wie es eine Menge von Vorverarbeitung zum Algorithmus hinzufügen würde.

Bearbeiten: Nur um etwas Kontext zu geben - dieser Algorithmus ist bereits geschrieben, und OpenMP wurde verwendet, um ziemlich gute Wirkung bei der Beschleunigung es. Allerdings verblassen die 8 Kerne auf meinem Entwicklungsrechner im Vergleich zu den 512 Kernen der GPU.

1voto

sastanin Punkte 38556

Kantenerkennung, Mittelwertberechnungen und Kreuzkorrelation können als 2D-Faltung implementiert werden. Faltungen können auf GPUs sehr effektiv implementiert werden ( Beschleunigung > 10, bis zu 100 in Bezug auf die CPU), insbesondere für große Kernel. Ja, es kann also sinnvoll sein, die Bildfilterung auf der GPU umzuschreiben.

Allerdings würde ich die GPU nicht als Entwicklungsplattform für eine solche Methode verwenden.

1voto

awdz9nld Punkte 1633

Da GPUs im Grunde SIMD-Maschinen sind, ist die Pipleline extrem anfällig für Pipeline-Stopps aufgrund von Verzweigungsfehlprognosen und leidet enorm darunter.

Wenn Sie der Meinung sind, dass die Verwendung eines Grafikprozessors erhebliche Vorteile bringt, sollten Sie einige vorläufige Benchmarks durchführen, um eine ungefähre Vorstellung zu erhalten.

Wenn Sie etwas darüber lernen wollen, wie man verzweigungsfreien Code schreibt, besuchen Sie http://cellperformance.beyond3d.com/ und sehen Sie es sich an.

Darüber hinaus könnte es sich lohnen, dieses Problem auf mehreren CPU-Kernen zu untersuchen. In diesem Fall sollten Sie sich entweder mit OpenCL oder den Intel-Leistungsbibliotheken (wie TBB) befassen.

Eine weitere Anlaufstelle für Probleme, die auf die GPU abzielen, sei es Grafik, rechnerische Geometrie oder anderes, ist IDAV, das Institut für Datenanalyse und Visualisierung: http://idav.ucdavis.edu

1voto

tkerwin Punkte 9061

Verzweigungen sind eigentlich gar nicht so schlecht, wenn sie räumlich kohärent sind. Mit anderen Worten: Wenn Sie erwarten, dass nebeneinander liegende Pixelblöcke im Bild dieselbe Verzweigung durchlaufen, wird der Leistungsverlust minimiert.

0voto

Ciaran Punkte 533

Die Verwendung eines Grafikprozessors für die Verarbeitung kann oft kontraintuitiv sein; Dinge, die offensichtlich ineffizient sind, wenn sie in normalem seriellen Code ausgeführt werden, lassen sich mit dem Grafikprozessor am besten parallel ausführen.

Der nachstehende Pseudocode sieht ineffizient aus (da er 8 gefilterte Werte für jedes Pixel berechnet), wird aber auf einem Grafikprozessor effizient ausgeführt:


# Compute the 8 possible filtered values for each pixel
for i = 1...8
    # filter[i] is the box filter that you want to apply
    # to pixels of the i'th edge-type
    result[i] = GPU_RunBoxFilter(filter[i], Image)

# Compute the edge type of each pixel
# This is the value you would normally use to 'switch' with
edge_type = GPU_ComputeEdgeType(Image)

# Setup an empty result image
final_result = zeros(sizeof(Image))
# For each possible switch value, replace all pixels of that edge-type
# with its corresponding filtered value
for i = 1..8
    final_result = GPU_ReplacePixelIfTrue(final_result, result[i], edge_type==i)

Hoffentlich hilft das!

0voto

Agnius Vasiliauskas Punkte 10637

Yep, Kontrollfluss hat in der Regel Leistungseinbußen auf GPU, sei es if's / switch'es / ternäre Operatoren denn bei Kontrollflussoperationen kann die GPU Threads nicht optimal ausführen. Die übliche Taktik besteht also darin, Verzweigungen so weit wie möglich zu vermeiden. In einigen Fällen können IFs durch Formeln ersetzt werden, wobei IF-Bedingungen auf Formelkoeffizienten abgebildet werden. Aber die konkrete Lösung/Optimierung hängt vom konkreten GPU-Kernel ab... Vielleicht können Sie den genauen Code zeigen, damit er von der Stackoverflow-Community weiter analysiert werden kann.

EDIT : Nur für den Fall, dass Sie interessiert sind, hier ist Faltungspixelshader die ich geschrieben habe.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X