packages feed

hw-rankselect-0.2.0.0: test/HaskellWorks/Data/Succinct/Excess/MinMaxExcess0Spec.hs

{-# OPTIONS_GHC -fno-warn-incomplete-patterns #-}
{-# LANGUAGE ScopedTypeVariables #-}

module HaskellWorks.Data.Succinct.Excess.MinMaxExcess0Spec (spec) where

import qualified Data.Vector.Storable                             as DVS
import           Data.Word
import           HaskellWorks.Data.Bits.Word
import           HaskellWorks.Data.Succinct.Excess.MinMaxExcess0
import           Test.Hspec
import           Test.QuickCheck

{-# ANN module ("HLint: Ignore Redundant do" :: String) #-}
{-# ANN module ("HLint: Ignore Reduce duplication"  :: String) #-}

spec :: Spec
spec = describe "HaskellWorks.Data.Succinct.Excess.MinMaxExcess0Spec" $ do
  describe "For Word8" $ do
    it "Excess should be between min excess and max excess" $
      forAll (choose (0, 255 :: Word8)) $ \w ->
        let (minE, e, maxE) = minMaxExcess0 w in
        minE <= e && e <= maxE
    it "minE2 == minE0 `min` (minE1 + e0)" $
      forAll (choose (0, 255 :: Word8)) $ \w0 ->
        forAll (choose (0, 255 :: Word8)) $ \w1 ->
          let w2 = leConcat w0 w1 in
          let (minE0, e0, _) = minMaxExcess0 w0 in
          let (minE1, _ , _) = minMaxExcess0 w1 in
          let (minE2, _ , _) = minMaxExcess0 w2 in
          minE2 == minE0 `min` (minE1 + e0)
    it "maxE2 == maxE0 `max` (maxE1 + e0)" $
      forAll (choose (0, 255 :: Word8)) $ \w0 ->
        forAll (choose (0, 255 :: Word8)) $ \w1 ->
          let w2 = leConcat w0 w1 in
          let (_, e0, maxE0) = minMaxExcess0 w0 in
          let (_, _ , maxE1) = minMaxExcess0 w1 in
          let (_, _ , maxE2) = minMaxExcess0 w2 in
          maxE2 == maxE0 `max` (maxE1 + e0)
    it "minE2 == minE0 `min` (minE1 + e0) via vector" $
      forAll (choose (0, 255 :: Word8)) $ \w0 ->
        forAll (choose (0, 255 :: Word8)) $ \w1 ->
          let w2 = DVS.fromList [w0, w1] in
          let (minE0, e0, _) = minMaxExcess0 w0 in
          let (minE1, _ , _) = minMaxExcess0 w1 in
          let (minE2, _ , _) = minMaxExcess0 w2 in
          minE2 == minE0 `min` (minE1 + e0)
    it "maxE2 == maxE0 `max` (maxE1 + e0) via vector" $
      forAll (choose (0, 255 :: Word8)) $ \w0 ->
        forAll (choose (0, 255 :: Word8)) $ \w1 ->
          let w2 = DVS.fromList [w0, w1] in
          let (_, e0, maxE0) = minMaxExcess0 w0 in
          let (_, _ , maxE1) = minMaxExcess0 w1 in
          let (_, _ , maxE2) = minMaxExcess0 w2 in
          maxE2 == maxE0 `max` (maxE1 + e0)
  describe "For Word16" $ do
    it "Excess should be between min excess and max excess" $
      forAll (choose (0, 255 :: Word16)) $ \w ->
        let (minE, e, maxE) = minMaxExcess0 w in
        minE <= e && e <= maxE
    it "minE2 == minE0 `min` (minE1 + e0)" $
      forAll (choose (0, 255 :: Word16)) $ \w0 ->
        forAll (choose (0, 255 :: Word16)) $ \w1 ->
          let w2 = leConcat w0 w1 in
          let (minE0, e0, _) = minMaxExcess0 w0 in
          let (minE1, _ , _) = minMaxExcess0 w1 in
          let (minE2, _ , _) = minMaxExcess0 w2 in
          minE2 == minE0 `min` (minE1 + e0)
    it "maxE2 == maxE0 `max` (maxE1 + e0)" $
      forAll (choose (0, 255 :: Word16)) $ \w0 ->
        forAll (choose (0, 255 :: Word16)) $ \w1 ->
          let w2 = leConcat w0 w1 in
          let (_, e0, maxE0) = minMaxExcess0 w0 in
          let (_, _ , maxE1) = minMaxExcess0 w1 in
          let (_, _ , maxE2) = minMaxExcess0 w2 in
          maxE2 == maxE0 `max` (maxE1 + e0)
    it "minE2 == minE0 `min` (minE1 + e0) via vector" $
      forAll (choose (0, 255 :: Word16)) $ \w0 ->
        forAll (choose (0, 255 :: Word16)) $ \w1 ->
          let w2 = DVS.fromList [w0, w1] in
          let (minE0, e0, _) = minMaxExcess0 w0 in
          let (minE1, _ , _) = minMaxExcess0 w1 in
          let (minE2, _ , _) = minMaxExcess0 w2 in
          minE2 == minE0 `min` (minE1 + e0)
    it "maxE2 == maxE0 `max` (maxE1 + e0) via vector" $
      forAll (choose (0, 255 :: Word16)) $ \w0 ->
        forAll (choose (0, 255 :: Word16)) $ \w1 ->
          let w2 = DVS.fromList [w0, w1] in
          let (_, e0, maxE0) = minMaxExcess0 w0 in
          let (_, _ , maxE1) = minMaxExcess0 w1 in
          let (_, _ , maxE2) = minMaxExcess0 w2 in
          maxE2 == maxE0 `max` (maxE1 + e0)
    describe "For Word32" $ do
      it "Excess should be between min excess and max excess" $
        forAll (choose (0, 255 :: Word32)) $ \w ->
          let (minE, e, maxE) = minMaxExcess0 w in
          minE <= e && e <= maxE
      it "minE2 == minE0 `min` (minE1 + e0)" $
        forAll (choose (0, 255 :: Word32)) $ \w0 ->
          forAll (choose (0, 255 :: Word32)) $ \w1 ->
            let w2 = leConcat w0 w1 in
            let (minE0, e0, _) = minMaxExcess0 w0 in
            let (minE1, _ , _) = minMaxExcess0 w1 in
            let (minE2, _ , _) = minMaxExcess0 w2 in
            minE2 == minE0 `min` (minE1 + e0)
      it "maxE2 == maxE0 `max` (maxE1 + e0)" $
        forAll (choose (0, 255 :: Word32)) $ \w0 ->
          forAll (choose (0, 255 :: Word32)) $ \w1 ->
            let w2 = leConcat w0 w1 in
            let (_, e0, maxE0) = minMaxExcess0 w0 in
            let (_, _ , maxE1) = minMaxExcess0 w1 in
            let (_, _ , maxE2) = minMaxExcess0 w2 in
            maxE2 == maxE0 `max` (maxE1 + e0)
      it "minE2 == minE0 `min` (minE1 + e0) via vector" $
        forAll (choose (0, 255 :: Word32)) $ \w0 ->
          forAll (choose (0, 255 :: Word32)) $ \w1 ->
            let w2 = DVS.fromList [w0, w1] in
            let (minE0, e0, _) = minMaxExcess0 w0 in
            let (minE1, _ , _) = minMaxExcess0 w1 in
            let (minE2, _ , _) = minMaxExcess0 w2 in
            minE2 == minE0 `min` (minE1 + e0)
      it "maxE2 == maxE0 `max` (maxE1 + e0) via vector" $
        forAll (choose (0, 255 :: Word32)) $ \w0 ->
          forAll (choose (0, 255 :: Word32)) $ \w1 ->
            let w2 = DVS.fromList [w0, w1] in
            let (_, e0, maxE0) = minMaxExcess0 w0 in
            let (_, _ , maxE1) = minMaxExcess0 w1 in
            let (_, _ , maxE2) = minMaxExcess0 w2 in
            maxE2 == maxE0 `max` (maxE1 + e0)
  describe "For Word64" $ do
    it "Excess should be between min excess and max excess" $
      forAll (choose (0, 255 :: Word64)) $ \w ->
        let (minE, e, maxE) = minMaxExcess0 w in
        minE <= e && e <= maxE
    it "minE2 == minE0 `min` (minE1 + e0) via vector" $
      forAll (choose (0, 255 :: Word64)) $ \w0 ->
        forAll (choose (0, 255 :: Word64)) $ \w1 ->
          let w2 = DVS.fromList [w0, w1] in
          let (minE0, e0, _) = minMaxExcess0 w0 in
          let (minE1, _ , _) = minMaxExcess0 w1 in
          let (minE2, _ , _) = minMaxExcess0 w2 in
          minE2 == minE0 `min` (minE1 + e0)
    it "maxE2 == maxE0 `max` (maxE1 + e0) via vector" $
      forAll (choose (0, 255 :: Word64)) $ \w0 ->
        forAll (choose (0, 255 :: Word64)) $ \w1 ->
          let w2 = DVS.fromList [w0, w1] in
          let (_, e0, maxE0) = minMaxExcess0 w0 in
          let (_, _ , maxE1) = minMaxExcess0 w1 in
          let (_, _ , maxE2) = minMaxExcess0 w2 in
          maxE2 == maxE0 `max` (maxE1 + e0)