packages feed

hashable 1.0.1.0 → 1.0.1.1

raw patch · 7 files changed

+148/−14 lines, 7 filesnew-uploaderPVP ok

version bump matches the API change (PVP)

API changes (from Hackage documentation)

Files

CHANGES view
@@ -1,4 +1,15 @@-= Version 1.0.0, 2010-08-15 =-^^^^^^^^^^^^^^^^^^^^^^^^^^^^^-* Separating Hashable class to its own package-from hashmap 1.0.0.3.+Version 1.0.1.1++* Fixed bug in Hashable instance for lazy ByteStrings where+  differences in the internal structure of the ByteString could cause+  different hash values for ByteStrings that are equal according to+  ==.++Version 1.0.1.0++* Added two helpers for creating Hashable instances: hashPtr and+  hashByteArray.++Version 1.0.0++* Separated Hashable class to its own package from hashmap 1.0.0.3.
Data/Hashable.hs view
@@ -151,8 +151,21 @@               B.unsafeUseAsCStringLen bs $ \(p, len) ->               hashPtr p (fromIntegral len) -instance Hashable BL.ByteString where hash = BL.foldlChunks hashAndCombine 0+-- The arguments to this function are flipped to make the function+-- easier to use with a left fold. +-- | Compute a hash value for this 'B.ByteString', using an initial+-- salt.+hashByteStringWithSalt :: Int           -- ^ salt+                       -> B.ByteString  -- ^ data to hash+                       -> Int           -- ^ hash value+hashByteStringWithSalt salt bs =+    B.inlinePerformIO $ B.unsafeUseAsCStringLen bs $ \(p, len) ->+    hashPtrWithSalt p (fromIntegral len) salt++instance Hashable BL.ByteString where+    hash = BL.foldlChunks hashByteStringWithSalt 0+ ------------------------------------------------------------------------ -- * Creating new instances @@ -192,9 +205,23 @@ hashPtr :: Ptr a      -- ^ pointer to the data to hash         -> Int        -- ^ length, in bytes         -> IO Int     -- ^ hash value-hashPtr p len =-    fromIntegral `fmap` hashByteString (castPtr p) (fromIntegral len)+hashPtr p len = hashPtrWithSalt p len 0 +-- | Compute a hash value for the content of this pointer, using an+-- initial salt.+--+-- This function can for example be used to hash non-contiguous+-- segments of memory as if they were one contiguous segment, by using+-- the output of one hash as the salt for the next.+hashPtrWithSalt :: Ptr a   -- ^ pointer to the data to hash+                -> Int     -- ^ length, in bytes+                -> Int     -- ^ salt+                -> IO Int  -- ^ hash value+hashPtrWithSalt p len salt =+    fromIntegral `fmap` hashCString (castPtr p) (fromIntegral len)+    (fromIntegral salt)++ #if defined(__GLASGOW_HASKELL__) -- | Compute a hash value for the content of this 'ByteArray#', -- beginning at the specified offset, using specified number of bytes.@@ -229,4 +256,5 @@ ------------------------------------------------------------------------ -- * Foreign imports -foreign import ccall unsafe hashByteString :: CString -> CInt -> IO CInt+foreign import ccall unsafe "djb_hash" hashCString+    :: CString -> CInt -> CInt -> IO CInt
+ README.md view
@@ -0,0 +1,7 @@+The hashable package+====================++This package defines a class, `Hashable`, for types that can be+converted to a hash value.  This class exists for the benefit of+hashing-based data structures.  The package provides instances for+basic types and a way to combine hash values.
+ benchmarks/Benchmarks.hs view
@@ -0,0 +1,59 @@+{-# LANGUAGE MagicHash, UnboxedTuples #-}++module Main (main) where++import Control.Monad.ST+import Criterion.Main+import Data.Hashable+import Foreign.ForeignPtr+import GHC.Exts+import GHC.ST (ST(..))++-- Benchmark English words (5 and 8), base64 encoded integers (11),+-- SHA1 hashes as hex (40), and large blobs (1 Mb).+main :: IO ()+main = do+    -- We do not actually care about the contents of these pointers.+    fp5 <- mallocForeignPtrBytes 5+    fp8 <- mallocForeignPtrBytes 8+    fp11 <- mallocForeignPtrBytes 11+    fp40 <- mallocForeignPtrBytes 40+    let !mb = 2^(20 :: Int)  -- 1 Mb+    fp1Mb <- mallocForeignPtrBytes mb+    +    -- We don't care about the contents of these either.+    let !ba5 = new 5+        !ba8 = new 8+        !ba11 = new 11+        !ba40 = new 40+        !ba1Mb = new mb+    +    withForeignPtr fp5 $ \ p5 ->+        withForeignPtr fp8 $ \ p8 ->+        withForeignPtr fp11 $ \ p11 ->+        withForeignPtr fp40 $ \ p40 ->+        withForeignPtr fp1Mb $ \ p1Mb ->+        defaultMain+        [ bgroup "hashPtr"+          [ bench "5" $ hashPtr p5 5+          , bench "8" $ hashPtr p8 8+          , bench "11" $ hashPtr p11 11+          , bench "40" $ hashPtr p40 40+          , bench "2^20" $ hashPtr p1Mb mb+          ]+        , bgroup "hashByteArray"+          [ bench "5" $ whnf (hashByteArray ba5 0) 5+          , bench "8" $ whnf (hashByteArray ba8 0) 8+          , bench "11" $ whnf (hashByteArray ba11 0) 11+          , bench "40" $ whnf (hashByteArray ba40 0) 40+          , bench "2^20" $ whnf (hashByteArray ba1Mb 0) mb+          ]+        ]++data ByteArray = BA { unBA :: !ByteArray# }++new :: Int -> ByteArray#+new (I# n#) = unBA $ runST $ ST $ \s1 ->+    case newByteArray# n# s1 of+        (# s2, ary #) -> case unsafeFreezeByteArray# ary s2 of+            (# s3, ba #) -> (# s3, BA ba #)
+ benchmarks/Makefile view
@@ -0,0 +1,25 @@+package := hashable+version := $(shell awk '/^Version:/{print $$2}' ../$(package).cabal)+lib := ../dist/build/libHS$(package)-$(version).a+ghc := ghc+ghc-flags := -Wall -O -hide-all-packages \+	-package-conf ../dist/package.conf.inplace -package base \+	-package hashable -package criterion \+	-package deepseq -package ghc-prim++%.o: %.hs+	$(ghc) $(ghc-flags) -c -o $@ $<++programs := bench++.PHONY: all+all: $(programs)++bench: $(lib) Benchmarks.o+	ranlib $(lib)+	$(ghc) $(ghc-flags) -threaded -o $@ $(filter %.o,$^) $(lib)++.PHONY: clean+clean:+	-find . \( -name '*.o' -o -name '*.hi' \) -exec rm {} \;+	-rm -f $(programs)
cbits/hashByteString.c view
@@ -1,6 +1,5 @@ /* Bernstein's hash */-int hashByteString(const char* str, int len) {-  int hash = 0;+int djb_hash(const char* str, int len, int hash) {    while (len--) {     hash = (hash * 33) ^ *str++;
hashable.cabal view
@@ -1,5 +1,5 @@ Name:                hashable-Version:             1.0.1.0+Version:             1.0.1.1 Synopsis:            A class for types that can be converted to a hash value Description:         This package defines a class, 'Hashable', for types that                      can be converted to a hash value.  This class@@ -16,8 +16,11 @@ Category:            Data Build-type:          Simple Cabal-version:       >=1.10-Extra-source-files:  CHANGES-+-- tests/Properties.hs shouldn't have to go here, but the source files+-- for the test-suite stanzas don't get picked up by `cabal sdist`.+Extra-source-files:+  CHANGES, README.md, tests/Properties.hs, benchmarks/Benchmarks.hs+  benchmarks/Makefile  Library   Default-language:  Haskell98@@ -27,6 +30,8 @@    C-sources:         cbits/hashByteString.c   Ghc-options:       -Wall+  if impl(ghc >= 6.8)+    Ghc-options: -fwarn-tabs  Test-suite tests   Default-language:  Haskell98@@ -42,4 +47,4 @@  source-repository head   type:     git-  location: http://github.com/tibbe/hashable.git+  location: https://github.com/tibbe/hashable.git