[英]Fast comparison of char arrays?
我目前正在一個代碼庫中工作,其中 IPv4 地址表示為指向u_int8
指針。 相等運算符是這樣實現的:
bool Ipv4Address::operator==(const u_int8 * inAddress) const
{
return (*(u_int32*) this->myBytes == *(u_int32*) inAddress);
}
這可能是禁食的解決方案,但它會導致 GCC 編譯器警告:
ipv4address.cpp:65: warning: dereferencing type-punned pointer will break strict-aliasing rules
如何在不破壞嚴格混疊規則且不損失性能點的情況下正確重寫比較?
我已經考慮使用memcmp
或這個宏:
#define IS_EQUAL(a, b) \
(a[0] == b[0] && a[1] == b[1] && a[2] == b[2] && a[3] == b[3])
我認為宏是最快的解決方案。
你有什么建議嗎?
更新
我剛剛閱讀了文章Squeezing performance out of memcmp usage ,它解釋了編譯器(Visual Studio,但也許還有 GCC)如何優化!memcmp(..)
調用。
我會去 memcmp()
還認為如果您的編譯器沒有內聯 memcmp() 您將遭受函數上下文切換
你確定你需要這么努力優化嗎? 您是否已經檢查過您的程序是否大部分時間都在執行此類操作?
您從 GCC 收到錯誤的原因是長度超過 1 個字節的任何內容都喜歡與對象大小倍數的地址對齊。 32 位整數喜歡從 32 位邊界開始。 char
變量(有符號、無符號或普通)可以位於任何字節邊界上,例如 3,它不適用於處理器的 32 位提取。
在您的情況下,對於 4 個字節(32 位),調用memcmp
開銷可能比實際比較字節的代碼要多。
嘗試這個:
bool Ipv4Address::operator==(const u_int8 * inAddress) const
{
return myBytes[0] == inAddress[0]
&& myBytes[1] == inAddress[1]
&& myBytes[2] == inAddress[2]
&& myBytes[3] == inAddress[3];
}
看媽,成員函數代碼不用this->
!
至於效率,這段代碼可能可以在調用memcpy
並從中執行 return 的同時執行(不執行memcpy
的內容)。 這是假設memcpy
沒有內聯。 知道編譯器庫是如何為通用和大型案例編寫的,我懷疑這段代碼仍然比memcpy
的內聯版本更小更快。 雖然證明是打印兩個版本的匯編列表並進行比較。
編輯:
注意:將實現聲明為內聯或將代碼放在類聲明中,比定義危險的宏要好。 它將更安全並且包含相同數量的代碼。 我喜歡內聯方法版本,因為它更具可讀性且更易於維護。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.