SSE (SIMD): Multiplikation Vektor mit skalaren
Einen gemeinsamen Betrieb, die ich tun in meinem Programm ist die Skalierung der Vektoren durch Skalare (V*s, z.B. [1,2,3,4]*2 == [2,4,6,8]). Gibt es eine SSE (oder AVX) die Anweisung, etwas zu tun, als der erste laden der Skalar in jeder position in einen Vektor (z.B. _mm_set_ps(2,2,2,2)) und dann multiplizieren?
Dies ist, was ich jetzt mache:
__m128 _scalar = _mm_set_ps(s,s,s,s);
__m128 _result = _mm_mul_ps(_vector, _scalar);
Ich bin auf der Suche nach so etwas wie...
__m128 _result = _mm_scale_ps(_vector, s);
Du musst angemeldet sein, um einen Kommentar abzugeben.
Je nach compiler, den Sie vielleicht in der Lage sein, den code zu verbessern-generation ein wenig mithilfe
_mm_set1_ps
:Doch Skalare Konstanten wie diesen sollte müssen nur einmal initialisiert, außerhalb der Schleifen, so dass die Leistung Kosten sollte irrelevant sein. (Es sei denn, der skalaren Wert ändert sich innerhalb der Schleife ?)
Wie immer sollten Sie sich die code-compiler generiert und auch versuchen, Ihren code unter eine anständige profiler, um zu sehen, wo die hotspots wirklich sind.
Gibt es keine Anweisung, die für die Multiplikation eines Vektors durch einen Skalar. Es gibt jedoch einige Anweisungen für das laden der gleichen skalaren Werte in alle Positionen in einem Vektor-register.
AVX-Befehlssatz bietet
_mm_broadcast_ss
/_mm256_broadcast_ss
/_mm256_broadcast_sd
- Interna für das Auffüllen von SSE-und AVX-Register mit der gleichen float/double-Wert.In den SSE3-Befehlssatz finden Sie möglicherweise
_mm_loaddup_pd
intrinsische füllt SSE-register mit dem gleichen double-Wert.In anderen Versionen von SSE in der Regel die beste option ist das laden eines skalaren Wert mit
_mm_load_ss
/_mm_load_sd
und dann kopieren Sie es, um alle Elemente der Vektor-register mit_mm_shuffle_ps
/_mm_unpacklo_pd
.Ich kenne keine einzige Anweisung, die tut, was Sie wollen. Wird die set-operation wirklich einen Engpass? Wenn Sie die Multiplikation eine große Vektor durch dieselbe Konstante, die Zeit, die es braucht, um füllen Sie ein XMM/YMM-register mit vier Kopien der Konstante muss einen sehr kleinen Bruchteil der gesamten Zeit genommen.
Als eine einfache Optimierung, wenn die Konstante 2, wie in deinem Beispiel, könnten Sie ersetzen Sie das multiplizieren mit einer add-Anweisung anstelle, nicht dass irgendwelche Konstanten.