2016-05-16 78 views
2

我對使用SSE的圖像中的像素執行按位非操作。上證所內在 - 邏輯非優化

我有一些問題:

  1. 可以這樣使用OpenMP進一步優化?
  2. 算法中是否有瓶頸可以優化?

這裏是我的代碼:

unsigned int iSSE2Size = (SrcImage1.GetHeight() * (SrcImage1.GetStepBytes() >> 1)) >> 3; 
__m128i *m_ucSrcPtr = (__m128i *)SrcImage1.GetWordPtr(); 
__m128i *m_ucDstPtr = (__m128i *)DestImage.GetWordPtr(); 
__m128i iMaxVal = _mm_set1_epi16(0xFFFF); 
unsigned short *srcRowPtr, *dstRowPtr; 
while (iSSE2Size-- > 0) 
{ 
    *m_ucDstPtr = _mm_andnot_si128(*m_ucSrcPtr, iMaxVal); 
    m_ucSrcPtr++; 
    m_ucDstPtr++; 
} 
+1

您是否試過循環展開? – Mehrdad

+1

你可以把它包裝在一個實際編譯的函數中,所以我們可以看看編譯器的輸出嗎? –

+1

爲什麼不使用'_mm_set1_epi16(65535)',讓編譯器擔心如何獲取數據。 (提示,它將比存儲到堆棧中的本地數組做更好的工作,然後從那裏加載,可以使用'pcmpeqw same,same'在運行中生成全部寄存器,並且CPU將該成語識別爲獨立於舊值,就像xor-zeroing一樣,讓編譯器爲你做這件事,但是) –

回答

0
  1. 是的,你可以嘗試這兩種循環展開,並使用OpenMP的優化你的代碼。

    #pragma omp parallel for 
    for (;iSSE2Size-=2 > 0;) 
    { 
        *m_ucDstPtr = _mm_andnot_si128(*m_ucSrcPtr, iMaxVal); 
        m_ucSrcPtr++; 
        m_ucDstPtr++; 
    
        *m_ucDstPtr = _mm_andnot_si128(*m_ucSrcPtr, iMaxVal); 
        m_ucSrcPtr++; 
        m_ucDstPtr++; 
    } 
    

    請注意,您可能會多次展開以提高性能。

  2. 我沒有看到您提供的代碼段中存在任何瓶頸。