سريع مزدوج -> تحويل قصير مع التثبيت باستخدام SSE؟
سؤال
هل هناك طريقة سريعة لإلقاء قيم مزدوجة على السراويل القصيرة (16 بتات موقعة) ، حاليًا أفعل شيئًا كهذا:
double dval = <sum junk>
int16_t sval;
if (val > int16_max) {
sval = int16_max;
} else if (val < int16_min) {
sval = int16_min;
} else
sval = (int16_t)val;
أظن أن هناك طريقة سريعة للقيام بذلك باستخدام SSE والتي ستكون أكثر كفاءة.
المحلول
ابحث عن minsd و maxsd و cvtsd2si ، أو إذا كنت ترغب في القيام 2 بالتوازي ، ثم استخدم minpd و maxpd و cvtpd2dq.
المكافأة الحقيقية الوحيدة لاستخدام الطريقة الأولى هي أن تحفظ الفروع. سيكون رمز SSE2 الذي تم إنشاؤه ، إلى حد كبير ، بالسرعة المزدوجة باستخدام رمز تم تجميعه إلى SSE2 على أي حال ... الفوز الحقيقي يأتي من القيام 2 منهم في وقت واحد.
تحرير: إذا أردت القيام بذلك باستخدام Visual Studio Intrinsics ، فأعتقد أن الكود سيبدو كما يلي:
__m128d sseDbl = _mm_set_sd( dbl );
sseDbl = _mm_min_sd( dbl, _mm_set_sd( 32767.0 ) );
sseDbl = _mm_max_sd( dbl, _mm_set_sd( -32768.0 ) );
short shrtVal = (short)_mm_cvtsd_si32( sseDbl );
والوظيفة القيام بها. إن القيام بذلك باستخدام Assembler متشابه جدًا أيضًا ، لكن ما سبق سيمنحك بالتأكيد أداء أفضل مع Visual Studio.