2024-02-02 21:37:18 -05:00
|
|
|
{-# LANGUAGE BangPatterns #-}
|
2019-09-22 09:20:03 -04:00
|
|
|
|
|
|
|
module Word16Tree
|
|
|
|
( Word16Tree
|
|
|
|
, encode
|
|
|
|
, exampleSmall
|
|
|
|
, example2000
|
|
|
|
, example9000
|
|
|
|
, expectedSmall
|
|
|
|
) where
|
|
|
|
|
|
|
|
import qualified Data.Bytes as Bytes
|
2024-02-02 21:37:18 -05:00
|
|
|
import Data.Bytes.Builder as B
|
2021-11-19 15:52:59 -05:00
|
|
|
import qualified Data.Bytes.Text.Ascii
|
2024-02-02 21:37:18 -05:00
|
|
|
import Data.Primitive (ByteArray)
|
|
|
|
import Data.Word (Word16)
|
2019-09-22 09:20:03 -04:00
|
|
|
|
|
|
|
data Word16Tree
|
|
|
|
= Branch !Word16Tree !Word16Tree
|
|
|
|
| Leaf {-# UNPACK #-} !Word16
|
|
|
|
|
|
|
|
encode :: Word16Tree -> Builder
|
|
|
|
encode (Leaf w) = B.word16PaddedUpperHex w
|
|
|
|
encode (Branch a b) =
|
|
|
|
B.ascii '('
|
2024-02-02 21:37:18 -05:00
|
|
|
<> encode a
|
|
|
|
<> B.ascii ','
|
|
|
|
<> encode b
|
|
|
|
<> B.ascii ')'
|
2019-09-22 09:20:03 -04:00
|
|
|
|
|
|
|
expectedSmall :: ByteArray
|
2024-02-02 21:37:18 -05:00
|
|
|
expectedSmall =
|
|
|
|
Bytes.toByteArray $
|
|
|
|
Data.Bytes.Text.Ascii.fromString
|
|
|
|
"((AB59,(1F33,2E71)),((((FA9A,247B),890C),(0F13,((55BF,7CF1),389B))),1205))"
|
2019-10-09 16:30:02 -04:00
|
|
|
|
2019-09-22 09:20:03 -04:00
|
|
|
exampleSmall :: Word16Tree
|
2024-02-02 21:37:18 -05:00
|
|
|
exampleSmall =
|
|
|
|
Branch
|
|
|
|
( Branch
|
|
|
|
(Leaf 0xAB59)
|
|
|
|
( Branch
|
|
|
|
(Leaf 0x1F33)
|
|
|
|
(Leaf 0x2E71)
|
2019-09-22 09:20:03 -04:00
|
|
|
)
|
2024-02-02 21:37:18 -05:00
|
|
|
)
|
|
|
|
( Branch
|
|
|
|
( Branch
|
|
|
|
( Branch
|
|
|
|
( Branch
|
|
|
|
(Leaf 0xFA9A)
|
|
|
|
(Leaf 0x247B)
|
|
|
|
)
|
|
|
|
(Leaf 0x890C)
|
|
|
|
)
|
|
|
|
( Branch
|
|
|
|
(Leaf 0x0F13)
|
|
|
|
( Branch
|
|
|
|
( Branch
|
|
|
|
(Leaf 0x55BF)
|
|
|
|
(Leaf 0x7CF1)
|
|
|
|
)
|
|
|
|
(Leaf 0x389B)
|
|
|
|
)
|
|
|
|
)
|
2019-09-22 09:20:03 -04:00
|
|
|
)
|
2024-02-02 21:37:18 -05:00
|
|
|
(Leaf 0x1205)
|
2019-09-22 09:20:03 -04:00
|
|
|
)
|
|
|
|
|
|
|
|
example2000 :: Word16Tree
|
2024-02-02 21:37:18 -05:00
|
|
|
{-# NOINLINE example2000 #-}
|
2019-09-22 09:20:03 -04:00
|
|
|
example2000 = balanced 0 2000
|
|
|
|
|
|
|
|
example9000 :: Word16Tree
|
2024-02-02 21:37:18 -05:00
|
|
|
{-# NOINLINE example9000 #-}
|
2019-09-22 09:20:03 -04:00
|
|
|
example9000 = balanced 0 9000
|
|
|
|
|
|
|
|
balanced :: Word16 -> Word16 -> Word16Tree
|
|
|
|
balanced !off !n
|
|
|
|
| n == 0 = Leaf off
|
|
|
|
| n == 1 = Leaf (off + 1)
|
2024-02-02 21:37:18 -05:00
|
|
|
| otherwise =
|
|
|
|
let x = div n 2
|
|
|
|
in Branch (balanced off x) (balanced (off + x) (n - x))
|