data StableName a
Stable names have the following property: If sn1 :: StableName and sn2 :: StableName and sn1 == sn2 then sn1 and sn2 were create
Holding the StableName
of an object doesn't prevent it from being garbage collected, whereas holding the object itself around (to use with reallyUnsafePtrEquality#
later) does. Sure, you can use System.Mem.Weak, but at that point, why not just use a StableName
? (In fact, weak pointers were added with StableName
s.)
Being able to hash them is the main motivator for StableName
s, as the documentation says:
We can't build a hash table using the address of the object as the key, because objects get moved around by the garbage collector, meaning a re-hash would be necessary after every garbage collection.
In general, if StableName
s will work for your purposes, I'd use them, even if you need to use unsafePerformIO
; if you really need reallyUnsafePtrEquality#
, you'll know. The only example I can think of where reallyUnsafePtrEquality#
would work and StableName
s wouldn't is speeding up an expensive Eq
instance:
x == y =
x `seq` y `seq`
case reallyUnsafePtrEquality# x y of
1# -> True
_ -> slowEq x y
There's probably other examples I just haven't thought of, but they're not common.