Optimization suggestions for writing a persistent vector definition for union struct

I wrote a stored vector instance for the data type below ( original question here ):

data Atoms = I GHC.Int.Int32 | S GHC.Int.Int16

Below is the code to define these instances for Storable vector. While I am getting very good performance with the code below, I am very interested in general suggestions to improve the performance of this persistent instance. By general sentence, I mean the following:

  • This does not apply to the GHC compiler version. You can assume that GHC 6.12.3+ eliminates performance errors if they are present in earlier versions and are related to this code.
  • Platform oriented offerings are fine. You can assume the Linux x86_64 platform.
  • A general proposal more in the form of an algorithm improvement (large O) is much appreciated than a proposal that uses hardware optimization. But, given a basic operation such as peek / poke here, there is little room for algorithmic improvement as far as I can tell (and therefore more valuable because it is a scarce product :)
  • Compiler flags for x86_64 are valid (for example, tell the compiler to delete a floating point check, etc.). I use the "-O2 -make" option to compile the code.

If there is any known good library source code that does a similar thing (i.e. defines persistent instances for union / recursive types), I will be very interested in checking them.

import Data.Vector.Storable
import qualified Data.Vector.Storable as V
import Foreign
import Foreign.C.Types
import GHC.Int

data Atoms = I GHC.Int.Int32 | S GHC.Int.Int16
                deriving (Show)

instance Storable Atoms where
  sizeOf _ = 1 + sizeOf (undefined :: Int32)
  alignment _ = 1 + alignment (undefined :: Int32)

  {-# INLINE peek #-}
  peek p = do
            let p1 = (castPtr p::Ptr Word8) `plusPtr` 1 -- get pointer to start of the    element. First byte is type of element
            t <- peek (castPtr p::Ptr Word8)
            case t of
              0 -> do
                    x <- peekElemOff (castPtr p1 :: Ptr GHC.Int.Int32) 0
                    return (I x)
              1 -> do
                    x <- peekElemOff (castPtr p1 :: Ptr GHC.Int.Int16) 0
                    return (S x)

  {-# INLINE poke #-}
  poke p x = case x of
      I a -> do
              poke (castPtr p :: Ptr Word8) 0
              pokeElemOff (castPtr p1) 0 a
      S a -> do
              poke (castPtr p :: Ptr Word8) 1
              pokeElemOff (castPtr p1) 0 a
      where  p1 = (castPtr p :: Ptr Word8) `plusPtr` 1 -- get pointer to start of the     element. First byte is type of element

Update:

Daniel dflemstr, , Word32 Word8. , , , , , - . , (. - # 49). , , 33% ( sum ). ( - , ):

:

data Atoms = I {-# UNPACK #-} !GHC.Int.Int32 | S {-# UNPACK #-} !GHC.Int.Int16

:

instance Storable Atoms where
  sizeOf _ = 2*sizeOf (undefined :: Int32)
  alignment _ = 4

  {-# INLINE peek #-}
  peek p = do
            let p1 = (castPtr p::Ptr Word32) `plusPtr` 1
            t <- peek (castPtr p::Ptr Word32)
            case t of
              0 -> do
                    x <- peekElemOff (castPtr p1 :: Ptr GHC.Int.Int32) 0
                    return (I x)
              _ -> do
                    x <- peekElemOff (castPtr p1 :: Ptr GHC.Int.Int16) 0
                    return (S x)

  {-# INLINE poke #-}
  poke p x = case x of
      I a -> do
              poke (castPtr p :: Ptr Word32) 0
              pokeElemOff (castPtr p1) 0 a
      S a -> do
              poke (castPtr p :: Ptr Word32) 1
              pokeElemOff (castPtr p1) 0 a
      where  p1 = (castPtr p :: Ptr Word32) `plusPtr` 1
+5
2

- , , .

, , , , 32- , , () , 32 4 ( 64- - 64 8 ). ; , , .

, 5 ( ), , :

|  32 bits  |  32 bits  |  32 bits  |  32 bits  |
 [    data    ] [    data    ] [    data    ]
 00 00 00 00 01 01 00 01 00 00 00 12 34 56 78 00
 IX Value       IX Value XX XX IX Value

IX = Constructor index
Value = The stored value
XX = Unused byte

, , / .

8 (64 ), :

|  32 bits  |  32 bits  |  32 bits  |  32 bits  |  32 bits  |  32 bits  |
 [    data    ]          [    data    ]          [    data    ]
 00 00 00 00 01 00 00 00 01 00 01 00 00 00 00 00 00 12 34 56 78 00 00 00
 IX Value       XX XX XX IX Value XX XX XX XX XX IX Value       XX XX XX

"" 3 , , .

8 , Int32, - , :

|  32 bits  |  32 bits  |  32 bits  |  32 bits  |  32 bits  |  32 bits  |
 [        data         ] [        data         ] [        data         ]
 00 00 00 00 00 00 00 01 00 00 00 01 00 01 00 00 00 00 00 00 12 34 56 78
 Index       Value       Index       Value XX XX Index       Value

, .

+1

, . , , 8- , 32 (Int32 Word32) Int32. , , . 64- , , 16 / Int64. , , , , .

+3

All Articles