GetHashCode и Equals неправильно реализованы в System.Attribute?

Вид из блога Artech ), а затем мы обсудили его в комментариях. Поскольку этот блог написан только на китайском языке, я кратко объясню здесь .Код для воспроизведения:

[AttributeUsage(AttributeTargets.Class, Inherited = true, AllowMultiple = true)]
public abstract class BaseAttribute : Attribute
{
    public string Name { get; set; }
}

public class FooAttribute : BaseAttribute { }

[Foo(Name = "A")]
[Foo(Name = "B")]
[Foo(Name = "C")]
public class Bar { }

//Main method
var attributes = typeof(Bar).GetCustomAttributes(true).OfType().ToList();
var getC = attributes.First(item => item.Name == "C");
attributes.Remove(getC);
attributes.ForEach(a => Console.WriteLine(a.Name));

Код получает все FooAttribute и удаляет тот, имя которого «C.». Очевидно, на выходе будут «A» и «B»? Если бы все шло гладко, вы бы не сделали этого. Я не вижу этот вопрос. На самом деле вы получите "AC", "BC" или даже правильное "AB" теоретически (у меня AC на моей машине, а у автора блога BC). Проблема возникает из-за реализации GetHashCode / Equals в System.Attribute. Фрагмент реализации:

  [SecuritySafeCritical]
  public override int GetHashCode()
  {
      Type type = base.GetType();
  // ***** УВЕДОМЛЕНИЕ *****
FieldInfo [] fields = type.GetFields (BindingFlags.NonPublic
 | BindingFlags.Public
 | BindingFlags.Instance);
      object obj2 = null;
      for (int i = 0; i < fields.Length; i++)
      {
          object obj3 = ((RtFieldInfo) fields[i]).InternalGetValue(this, false, false);
          if ((obj3 != null) && !obj3.GetType().IsArray)
          {
              obj2 = obj3;
          }
          if (obj2 != null)
          {
              break;
          }
      }
      if (obj2 != null)
      {
          return obj2.GetHashCode();
      }
      return type.GetHashCode();
  }

Он использует Type.GetFields , поэтому свойства, унаследованные от базового класса, игнорируются, отсюда эквивалентность трех экземпляров FooAttribute (а затем Remove ] метод принимает один случайным образом ). Итак, вопрос: есть ли какая-то особая причина для реализации? Или это просто ошибка?

14
задан Cheng Chen 12 January 2012 в 17:26
поделиться