4e987026 |
module PreludeTuple where
{-#Prelude#-} -- Indicates definitions of compiler prelude symbols
import PreludeTuplePrims
-- This module contains support routines which handle tuple instances.
-- These are based on a implementation level data type which represents
-- general tuples and a data type to hold the set of dictionaries which
-- are associated with the tuple.
-- Each of these functions takes the tupledicts as the first argument.
-- Force all of these functions to take strict arguments because they'll
-- never be called with 0-length tuples anyway.
-- The following primitives operate on tuples.
-- tupleSize :: TupleDicts -> Int
-- tupleSel :: Tuple -> Int -> Int -> a
-- dictSel :: TupleDicts -> method -> Int -> a
-- listToTuple :: [a] -> Tuple
-- Eq functions
tupleEq :: TupleDicts -> Tuple -> Tuple -> Bool
{-# tupleEq :: Strictness("S,S,S") #-}
tupleEq dicts x y = tupleEq1 0 where
tupleEq1 i | i == size = True
| otherwise =
((dictSel (cmpEq dicts i)) x' y') && tupleEq1 (i+1)
where
x' = tupleSel x i size
y' = tupleSel y i size
size = tupleSize dicts
cmpEq x y = x == y
tupleNeq dicts x y = not (tupleEq dicts x y)
-- Ord functions
tupleLe :: TupleDicts -> Tuple -> Tuple -> Bool
{-# tupleLe :: Strictness("S,S,S") #-}
tupleLe dicts x y = tupleLe1 0 where
tupleLe1 i | i == size = False
| (dictSel (cmpLs dicts i)) x' y' = True
| (dictSel (ordEq dicts i)) x' y' = tupleLe1 (i+1)
| otherwise = False
where
x' = tupleSel x i size
y' = tupleSel y i size
size = tupleSize dicts
cmpLs x y = x < y
ordEq :: Ord a => a -> a -> Bool
ordEq x y = x == y
tupleLeq :: TupleDicts -> Tuple -> Tuple -> Bool
{-# tupleLeq :: Strictness("S,S,S") #-}
tupleLeq dicts x y = tupleLeq1 0 where
tupleLeq1 i | i == size = True
| (dictSel (cmpLs dicts i)) x' y' = True
| (dictSel (ordEq dicts i)) x' y' = tupleLeq1 (i+1)
| otherwise = False
where
x' = tupleSel x i size
y' = tupleSel y i size
size = tupleSize dicts
tupleGe :: TupleDicts -> Tuple -> Tuple -> Bool
tupleGe d x y = tupleLe d y x
tupleGeq :: TupleDicts -> Tuple -> Tuple -> Bool
tupleGeq d x y = tupleLeq d y x
tupleMax,tupleMin :: TupleDicts -> Tuple -> Tuple -> Tuple
tupleMax d x y = if tupleGe d x y then x else y
tupleMin d x y = if tupleLe d x y then x else y
-- Ix functions
tupleRange :: TupleDicts -> (Tuple,Tuple) -> [Tuple]
{-# tupleRange :: Strictness("S,S") #-}
tupleRange dicts (x,y) = map listToTuple (tupleRange' 0) where
tupleRange' i | i == size = [[]]
| otherwise =
[(i1 : i2) | i1 <- r, i2 <- tupleRange' (i+1)]
where
x' = tupleSel x i size
y' = tupleSel y i size
r = (dictSel (range' dicts i)) (x',y')
size = tupleSize dicts
range' x = range x
tupleIndex :: TupleDicts -> (Tuple,Tuple) -> Tuple -> Int
{-# tupleIndex :: Strictness("S,S,S") #-}
tupleIndex dicts (low,high) n = tupleIndex' (size-1) where
size = tupleSize dicts
tupleIndex' i | i == 0 = i'
| otherwise = i' + r' * (tupleIndex' (i-1))
where
low' = tupleSel low i size
high' = tupleSel high i size
n' = tupleSel n i size
i' = (dictSel (index' dicts i)) (low',high') n'
r' = (dictSel (rangeSize dicts i)) (low',high')
index' x = index x
rangeSize :: (Ix a) => (a,a) -> Int
rangeSize (l,u) = index (l,u) u + 1
tupleInRange :: TupleDicts -> (Tuple,Tuple) -> Tuple -> Bool
{-# tupleInRange :: Strictness("S,S,S") #-}
tupleInRange dicts (low,high) n = tupleInRange' 0 where
size = tupleSize dicts
tupleInRange' i | i == size = True
| otherwise = (dictSel (inRange' dicts i)) (low',high') n'
&& tupleInRange' (i+1)
where
low' = tupleSel low i size
high' = tupleSel high i size
n' = tupleSel n i size
inRange' x = inRange x
-- Text functions
tupleReadsPrec :: TupleDicts -> Int -> ReadS Tuple
tupleReadsPrec dicts p = readParen False
(\s -> map ( \ (t,w) -> (listToTuple t,w))
(tRP' s 0))
where
size = tupleSize dicts
tRP' s i | i == 0 = [(t':t,w) |
("(",s1) <- lex s,
(t',s2) <- nextItem s1,
(t,w) <- tRP' s2 (i+1)]
| i == size = [([],w) | (")",w) <- lex s]
| otherwise =
[(t':t,w) |
(",",s1) <- lex s,
(t',s2) <- nextItem s1,
(t,w) <- tRP' s2 (i+1)]
where
nextItem s = (dictSel (reads dicts i)) s
tupleShowsPrec :: TupleDicts -> Int -> Tuple -> ShowS
tupleShowsPrec dicts p tuple =
showChar '(' . tSP' 0
where
size = tupleSize dicts
tSP' i | i == (size-1) =
showTup . showChar ')'
| otherwise =
showTup . showChar ',' . tSP' (i+1)
where
showTup = (dictSel (shows dicts i)) (tupleSel tuple i size)
tupleReadList :: TupleDicts -> ReadS [Tuple]
tupleReadList dicts =
readParen False (\r -> [pr | ("[",s) <- lex r,
pr <- readl s])
where readl s = [([],t) | ("]",t) <- lex s] ++
[(x:xs,u) | (x,t) <- tupleReads s,
(xs,u) <- readl' t]
readl' s = [([],t) | ("]",t) <- lex s] ++
[(x:xs,v) | (",",t) <- lex s,
(x,u) <- tupleReads t,
(xs,v) <- readl' u]
tupleReads s = tupleReadsPrec dicts 0 s
tupleShowList :: TupleDicts -> [Tuple] -> ShowS
tupleShowList dicts [] = showString "[]"
tupleShowList dicts (x:xs)
= showChar '[' . showsTuple x . showl xs
where showl [] = showChar ']'
showl (x:xs) = showString ", " . showsTuple x
. showl xs
showsTuple x = tupleShowsPrec dicts 0 x
-- Binary functions
tupleShowBin :: TupleDicts -> Tuple -> Bin -> Bin
tupleShowBin dicts t bin = tSB' 0
where
size = tupleSize dicts
tSB' i | i == size = bin
tSB' i | otherwise =
(dictSel (showBin' dicts i)) (tupleSel t i size) (tSB' (i+1))
showBin' x = showBin x
tupleReadBin :: TupleDicts -> Bin -> (Tuple,Bin)
tupleReadBin dicts bin = (listToTuple t,b) where
size = tupleSize dicts
(t,b) = tRB' bin 0
tRB' b i | i == size = ([],b)
| otherwise = (t':ts,b') where
(t',b'') = (dictSel (readBin' dicts i)) b
(ts,b') = tRB' b'' (i+1)
readBin' x = readBin x
|