![](/img/trans.png)
[英]How do I write a reliable content-independent implementation of memcmp()?
[英]How to do reverse memcmp?
如何進行反向內存比較? 如上所示,我給出了兩個序列的結尾,並且我希望指針朝着開頭遞減,而不是朝着結尾遞增。
C標准庫中沒有內置函數可以執行此操作。 這是滾動自己的簡單方法:
int memrcmp(const void *s1, const void *s2, size_t n)
{
if(n == 0)
return 0;
// Grab pointers to the end and walk backwards
const unsigned char *p1 = (const unsigned char*)s1 + n - 1;
const unsigned char *p2 = (const unsigned char*)s2 + n - 1;
while(n > 0)
{
// If the current characters differ, return an appropriately signed
// value; otherwise, keep searching backwards
if(*p1 != *p2)
return *p1 - *p2;
p1--;
p2--;
n--;
}
return 0;
}
如果您具有高性能,則應該一次比較4個字節的字而不是單個字節,因為內存延遲將成為瓶頸。 但是,該解決方案要復雜得多,並不值得。
就像最初由弗拉德·拉扎連科(Vlad Lazarenko)鏈接的帖子( 反向C memcpy )中一樣,這是基於此的解決方案,我尚未測試過,但應該讓您入門。
int reverse_memcmp(const void *s1, const void *s2, size_t n)
{
unsigned char *a, *b;
a = s1;
b = s2;
size_t i = 0;
// subtracting i from last position and comparing
for (i = 0; i < n; i++) {
if (a[n-1-i] != b[n-1-i]) {
// return differences between different byte, strcmp()-style
return (a[n-1-i] - b[n-1-i]);
}
}
return 0;
}
較短的代碼(C代碼不需要強制指針類型強制轉換):
int reverse_memcmp(const void *end1, const void *end2, size_t n) {
const unsigned char *a = end1, *b = end2;
for (; n; --n)
if (*--a != *--b) return *a - *b;
return 0;
}
您所需要做的就是指定兩端,要比較的大小以及步長。 請特別注意,步長可能是獲得預期結果的最重要部分。 如果限制大小,它將大大簡化實現。 對於char的大小,您可以執行以下操作:
int compare (void *one, void *two, size_t size)
{
char *one_char = (char *)one;
char *two_char = (char *)two;
size_t i;
for (i = 0; i < size; i++)
{
if (*(one_char - i) != *(two_char - i))
return(NOT_EQUAL);
}
return(EQUAL);
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.