简体   繁体   English

Arraylist在从磁盘加载后无法比较对象

[英]Arraylist can't compare objects after they are loaded from disk

To make it easy, lets say I have an arraylist allBooks containing class "books" and an arraylist someBooks containing some but not all of the "books". 为了方便arraylist allBooks ,让我说我有一个arraylist allBooks包含类“书”和一个arraylist someBooks包含一些但不是所有的“书”。

Using contains() method worked fine when I wanted to see if a book from one arraylist was also contained in another. 当我想看一个arraylist中的一本书是否也包含在另一个arraylist中时,使用contains()方法工作正常。

The problem was that this isn't working anymore when I save both of the Arraylists to a .bin file and load them back once the program restarts. 问题是,当我将两个Arraylists保存到.bin文件并在程序重新启动后加载它们时,这不再起作用了。 Doing the same test as before, the contains() returns false even if the compared objects are the same (have the same info inside). 执行与以前相同的测试,即使比较的对象相同(内部具有相同的信息),contains()也返回false。

I solved it by overloading the equals method and it works fine, but I want to know why did this happen? 我通过重载equals方法解决了它,它工作正常,但我想知道为什么会发生这种情况?

You will have to provide your own hash code and equals implementation. 您必须提供自己的哈希码并等于实现。 By default, it will simply use pointer equality, which obviously fails after objects been 'cloned' (serialized/ deserialized cycle). 默认情况下,它只会使用指针相等,这在对象被“克隆”(序列化/反序列化循环)后显然会失败。

What happened was that when you originally created the lists they both contained references to the same objects, but when you loaded them back in they both got separate copies of the same objects. 发生的事情是,当您最初创建列表时,它们都包含对相同对象的引用,但是当您将它们加载回来时,它们都获得了相同对象的单独副本。 Since each list got separate copies, they didn't contain the same references, meaning they didn't compare as equal without overloading the right method. 由于每个列表都有单独的副本,因此它们不包含相同的引用,这意味着它们不会在没有重载正确方法的情况下进行比较。

This sounds like the common issue of referential equality vs Equals , and is especially common with serialization. 这听起来像是引用平等与Equals的共同问题,在序列化中尤为常见。 Override Equals (and GetHashCode ) appropriately and you should be back in business. 适当地覆盖Equals (和GetHashCode ),你应该重新开始工作。

For info, using ArrayList should generally be avoided unless you are using .NET 1.1 (or micro-framework), or have a very valid reason to do so; 有关信息, 通常应避免使用ArrayList除非您使用的是.NET 1.1(或微框架),或者有非常有效的理由这样做; prefer the generic typed collections, such as List<T> . 更喜欢通用类型集合,例如List<T>

Assuming book is an object, by default Equals checks if the reference is equal. 假设book是一个对象,默认情况下Equals检查引用是否相等。 That cannot be the case when you load new objects. 加载新对象时不会出现这种情况。 Overwriting the Equals method is a right approach. 覆盖Equals方法是一种正确的方法。
Other options are to change Book to a struct, or using a more modern container, like a dictionary or hashtable, where you can store books by id. 其他选项是将Book更改为结构,或使用更现代的容器,如字典或哈希表,您可以通过id存储书籍。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 比较从不同程序集加载的对象 - Compare objects loaded from different assemblies 将文件写入磁盘后无法执行文件 - Can´t execute file after writing it to the disk 从加载的程序集中查找实现接口的对象 - 如何比较类型? - Finding objects that implement interface from loaded assembly -how to compare types? 如何链接从磁盘外部加载的资源字典,不包含在项目或程序集中? - How can I chain Resource Dictionaries that are externally loaded from disk, not included in project or assembly? 无法覆盖 Equals 时如何比较两个对象? - How to compare two objects when you can't override Equals? 从对象的数组列表中删除重复项 - Remove duplicates from arraylist of objects 无法将 object 从 Arraylist 与实际的 object 进行比较 - Cannot compare object from Arraylist to the actual object 无法加载LoadStateEventArgs - LoadStateEventArgs can't loaded 使用json.net反序列化后无法从Dictionary投射对象 - Can't cast objects from Dictionary after using json.net deserialization 如何获得DataAnnotations.Compare来比较2个不同对象的属性? - How can I get DataAnnotations.Compare to compare properties from 2 different objects?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM