Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

FlatHashTable and things that depend on it like mutable.HashSet cannot store nulls #6908

Closed
scabug opened this issue Jan 3, 2013 · 6 comments

Comments

@scabug
Copy link

scabug commented Jan 3, 2013

mutable.HashSet or anything that depends on FlatHashTable for its implementation cannot have null values. But allowing it to support null is easy and would extend the functionality nicely

scala> val h = new scala.collection.mutable.HashSet[String]
h: scala.collection.mutable.HashSet[String] = Set()

scala> h.contains(null)
java.lang.IllegalArgumentException: Flat hash tables cannot contain null elements.
at scala.collection.mutable.FlatHashTable$HashUtils$class.elemHashCode(FlatHashTable.scala:348)
at scala.collection.mutable.HashSet.elemHashCode(HashSet.scala:41)
at scala.collection.mutable.FlatHashTable$class.containsEntry(FlatHashTable.scala:109)
at scala.collection.mutable.HashSet.containsEntry(HashSet.scala:41)
at scala.collection.mutable.HashSet.contains(HashSet.scala:57)
...

You might think "oh, let's just make contains smart about null" but look at this

scala> val xs = null :: Nil
xs: List[Null] = List(null)

scala> xs.distinct
java.lang.IllegalArgumentException: Flat hash tables cannot contain null elements.
...etc

now, making contains not explode on null would prevent that stack trace...but the resulting set would be empty even though the original list was not. I contend that doesn't make sense and that the only thing that does make sense is to make FlatHashTable allow nulls just as List does.

@scabug
Copy link
Author

scabug commented Jan 3, 2013

Imported From: https://issues.scala-lang.org/browse/SI-6908?orig=1
Reporter: @JamesIry
Affected Versions: 2.9.2
See #3630

@scabug
Copy link
Author

scabug commented Jan 3, 2013

Ievgen Platonov (jozic) said (edited by @paulp on Jan 4, 2013 12:09:23 AM UTC):
Another interesting implication

scala> val l = null :: Nil
l: List[Null] = List(null)

scala> l.distinct
java.lang.IllegalArgumentException: Flat hash tables cannot contain null elements.
at scala.collection.mutable.FlatHashTable$HashUtils$class.elemHashCode(FlatHashTable.scala:348)
at scala.collection.mutable.HashSet.elemHashCode(HashSet.scala:41)
at scala.collection.mutable.FlatHashTable$class.containsEntry(FlatHashTable.scala:109)

@scabug
Copy link
Author

scabug commented Jan 4, 2013

@paulp said:
Transplanting my github comment:

"It's pretty sad that there is this protected method "removeElem" which insists on allocating a Some and returning the removed element in it - which is then NEVER USED ANYWHERE. The only uses to which the return value are put are "isDefined" and tossing it aside. Given that object FlatHashTable is private[collection], it's pretty unlikely it does that for the benefit of code which is not in trunk."

@scabug
Copy link
Author

scabug commented Jan 5, 2013

@adriaanm said:
scala/scala#1839

@scabug
Copy link
Author

scabug commented Feb 3, 2014

@adriaanm said:
reopening based on report at cheeseng/scalatest@f28781d#commitcomment-5137058

scala> val set = collection.mutable.Set("1", null, "3").par
set: scala.collection.parallel.mutable.ParSet[String] = ParHashSet(null, 3, 1)

scala> set.exists(_ == null)
java.lang.ClassCastException: scala.collection.mutable.FlatHashTable$NullSentinel$ cannot be cast to java.lang.String
at $anonfun$1.apply(:9)
at scala.collection.Iterator$class.exists(Iterator.scala:769)

@scabug
Copy link
Author

scabug commented Feb 14, 2014

@Ichoran said:
scala/scala#3528

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants