Skip to content

Commit

Permalink
CLJ-1766: Serializing+deserializing lists breaks their hash
Browse files Browse the repository at this point in the history
Lists declare their `hash` and `hasheq` fields as transients, which are
deserialized with default value `0`, breaking the expectation of
non-computed values. Transients are meant to be non-serialized by
default, so changing `0` to be non-computed on this case is not only
more natural but also fixes the serialization roundtrip.

Signed-off-by: Stuart Halloway <stu@cognitect.com>
  • Loading branch information
andrewhr authored and stuarthalloway committed Sep 3, 2015
1 parent 1d5237f commit bd6e906
Show file tree
Hide file tree
Showing 2 changed files with 7 additions and 5 deletions.
8 changes: 4 additions & 4 deletions src/jvm/clojure/lang/ASeq.java
Expand Up @@ -14,8 +14,8 @@
import java.util.*;

public abstract class ASeq extends Obj implements ISeq, Sequential, List, Serializable, IHashEq {
transient int _hash = -1;
transient int _hasheq = -1;
transient int _hash;
transient int _hasheq;

public String toString(){
return RT.printString(this);
Expand Down Expand Up @@ -62,7 +62,7 @@ public boolean equals(Object obj){
}

public int hashCode(){
if(_hash == -1)
if(_hash == 0)
{
int hash = 1;
for(ISeq s = seq(); s != null; s = s.next())
Expand All @@ -75,7 +75,7 @@ public int hashCode(){
}

public int hasheq(){
if(_hasheq == -1)
if(_hasheq == 0)
{
// int hash = 1;
// for(ISeq s = seq(); s != null; s = s.next())
Expand Down
4 changes: 3 additions & 1 deletion test/clojure/test_clojure/serialization.clj
Expand Up @@ -43,7 +43,9 @@
rt-seq (-> v seq serialize deserialize)]
(and (= v rt)
(= (seq v) (seq rt))
(= (seq v) rt-seq))))
(= (seq v) rt-seq)
(= (hash v) (hash rt))
(= (.hashCode v) (.hashCode rt)))))

(deftest sequable-serialization
(are [val] (roundtrip val)
Expand Down

0 comments on commit bd6e906

Please sign in to comment.