在.NET中有任何类型的"ReferenceComparer"吗?

alp*_*use 18 .net c# comparison base-class-library

BCL中有几个地方可以使用IEqualityComparer.像Enumerable.ContainsDictionary Constructor.如果我对默认的不满意,我可以提供我的比较器.

有时我想知道集合是否包含我所引用的那个对象.不是任何其他意义上被认为"相等"的那个.
问题是:BCL中是否存在仅依赖于ReferenceEquals方法的标准相等比较器?

我自己写的是这样的:

class ReferenceComparer<T> : IEqualityComparer<T> where T : class
{
    private static ReferenceComparer<T> m_instance;

    public static ReferenceComparer<T> Instance
    {
        get
        {
            return m_instance ?? (m_instance = new ReferenceComparer<T>());
        }
    }

    public bool Equals(T x, T y)
    {
        return ReferenceEquals(x, y);
    }

    public int GetHashCode(T obj)
    {
        return RuntimeHelpers.GetHashCode(obj);
    }
}
Run Code Online (Sandbox Code Playgroud)

我没有测试它彻底,也没有考虑很多的场景,但它似乎使Enumerable.ContainsDictionary很高兴.

Ani*_*Ani 17

据我所知,自IEqualityComparer<T>.NET 4.0起,BCL不公开任何使用引用相等实现的公共类型.

但是,似乎有一堆内部类型可以做到这一点,例如:

  • System.Dynamic.Utils.ReferenceEqualityComparer<T> (在System.Core中)
  • System.Xaml.Schema.ReferenceEqualityComparer<T> (在System.Xaml中).

我用反射器看了这两种类型的实现,你会很高兴地知道它们似乎都以你的几乎完全相同的方式实现,除了它们不使用延迟初始化对于静态实例(它们在类型的静态构造函数中创建它).

我可以想到的唯一可能的'问题'是你的实现是懒惰初始化不是线程安全的,但由于实例是"便宜的"并且没有保持任何状态,所以不应该创建任何错误或主要性能问题.如果你想强制执行单例模式,你必须正确地执行它.