比较 .NET 中的两个字节数组 [英] Comparing two byte arrays in .NET

查看:35
本文介绍了比较 .NET 中的两个字节数组的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我怎样才能快速做到这一点?

How can I do this fast?

我当然可以:

static bool ByteArrayCompare(byte[] a1, byte[] a2)
{
    if (a1.Length != a2.Length)
        return false;

    for (int i=0; i<a1.Length; i++)
        if (a1[i]!=a2[i])
            return false;

    return true;
}

但我正在寻找 BCL 函数或一些高度优化的行之有效的方法来做到这一点.

But I'm looking for either a BCL function or some highly optimized proven way to do this.

java.util.Arrays.equals((sbyte[])(Array)a1, (sbyte[])(Array)a2);

效果很好,但似乎不适用于 x64.

works nicely, but it doesn't look like that would work for x64.

这里注意我的超快速回答.

Note my super-fast answer here.

推荐答案

用户 gil 建议的不安全代码产生了这个解决方案:

User gil suggested unsafe code which spawned this solution:

// Copyright (c) 2008-2013 Hafthor Stefansson
// Distributed under the MIT/X11 software license
// Ref: http://www.opensource.org/licenses/mit-license.php.
static unsafe bool UnsafeCompare(byte[] a1, byte[] a2) {
  if(a1==a2) return true;
  if(a1==null || a2==null || a1.Length!=a2.Length)
    return false;
  fixed (byte* p1=a1, p2=a2) {
    byte* x1=p1, x2=p2;
    int l = a1.Length;
    for (int i=0; i < l/8; i++, x1+=8, x2+=8)
      if (*((long*)x1) != *((long*)x2)) return false;
    if ((l & 4)!=0) { if (*((int*)x1)!=*((int*)x2)) return false; x1+=4; x2+=4; }
    if ((l & 2)!=0) { if (*((short*)x1)!=*((short*)x2)) return false; x1+=2; x2+=2; }
    if ((l & 1)!=0) if (*((byte*)x1) != *((byte*)x2)) return false;
    return true;
  }
}

对尽可能多的数组进行基于 64 位的比较.这种依赖于数组开始 qword 对齐的事实.如果不是 qword 对齐,它会起作用,只是没有它那么快.

which does 64-bit based comparison for as much of the array as possible. This kind of counts on the fact that the arrays start qword aligned. It'll work if not qword aligned, just not as fast as if it were.

它比简单的 for 循环执行大约快 7 个计时器.使用 J# 库与原始 for 循环等效.使用 .SequenceEqual 运行速度大约慢七倍;我认为只是因为它使用的是 IEnumerator.MoveNext.我想基于 LINQ 的解决方案至少会那么慢或更糟.

It performs about seven timers faster than the simple for loop. Using the J# library performed equivalently to the original for loop. Using .SequenceEqual runs around seven times slower; I think just because it is using IEnumerator.MoveNext. I imagine LINQ-based solutions being at least that slow or worse.

这篇关于比较 .NET 中的两个字节数组的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆