【问题标题】:Arraylist can't compare objects after they are loaded from disk从磁盘加载对象后,Arraylist 无法比较对象
【发布时间】:2011-02-12 06:35:53
【问题描述】:

为了简单起见,假设我有一个包含类“books”的arraylist allBooks 和一个包含一些但不是全部“books”的arraylist someBooks

当我想查看一个数组列表中的一本书是否也包含在另一个数组中时,使用 contains() 方法效果很好。

问题是,当我将两个 Arraylist 保存到 .bin 文件并在程序重新启动后将它们加载回来时,这不再起作用。进行与之前相同的测试,即使比较的对象相同(内部具有相同的信息), contains() 也会返回 false。

我通过重载equals方法解决了它,它工作正常,但我想知道为什么会发生这种情况?

【问题讨论】:

  • 旁注:为什么不使用List<Book> 而不是ArrayList
  • 您使用什么机制将它们写入磁盘?

标签: c# arraylist


【解决方案1】:

您必须提供自己的哈希码和 equals 实现。默认情况下,它将简单地使用指针相等,这在对象被“克隆”(序列化/反序列化循环)后显然会失败。

【讨论】:

  • 谢谢。完全忘记了加载后指针会不一样。
【解决方案2】:

发生的情况是,当您最初创建列表时,它们都包含对相同对象的引用,但当您将它们重新加载时,它们都获得了相同对象的单独副本。由于每个列表都有单独的副本,因此它们不包含相同的引用,这意味着如果不重载正确的方法,它们就不会进行相等比较。

【讨论】:

    【解决方案3】:

    这听起来像是引用相等与Equals 的常见问题,在序列化中尤其常见。适当地覆盖Equals(和GetHashCode),您应该会重新开始工作。

    对于信息,应该一般避免使用ArrayList,除非您使用.NET 1.1(或微框架),或者有非常正当的理由这样做;更喜欢泛型类型的集合,例如List<T>

    【讨论】:

      【解决方案4】:

      假设book 是一个对象,默认情况下Equals 检查引用是否相等。当您加载新对象时,情况并非如此。覆盖Equals 方法是正确的方法。
      其他选项是将Book 更改为结构,或者使用更现代的容器,如字典或哈希表,您可以在其中按 id 存储书籍。

      【讨论】:

      • 我不会说字典/哈希表“更现代”——它们只是用于不同的目的。
      • @Marc - 公平点。我显然对 .net 的版本有偏见。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2014-12-10
      • 1970-01-01
      • 1970-01-01
      • 2020-05-12
      • 1970-01-01
      • 1970-01-01
      • 2016-07-11
      相关资源
      最近更新 更多