-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathsorting.hs
71 lines (59 loc) · 2.07 KB
/
sorting.hs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
import Data.List
import Test.FitSpec
ordered :: Ord a => [a] -> Bool
ordered [] = True
ordered [_] = True
ordered (x:y:xs) = x <= y && ordered (y:xs)
permutation :: Eq a => [a] -> [a] -> Bool
[] `permutation` [] = True
(_:_) `permutation` [] = False
[] `permutation` (_:_) = False
(x:xs) `permutation` ys = x `elem` ys && xs `permutation` delete x ys
count :: Eq a => a -> [a] -> Int
count x = length . filter (==x)
properties :: (Ord a, Show a, Listable a)
=> ([a] -> [a]) -> [Property]
properties sort =
[ property $ \xs -> ordered (sort xs)
, property $ \xs -> length (sort xs) == length xs
, property $ \x xs -> elem x (sort xs) == elem x xs
, property $ \x xs -> count x (sort xs) == count x xs
, property $ \xs -> permutation xs (sort xs)
, property $ \x xs -> insert x (sort xs) == sort (x:xs)
]
sargs :: Args
sargs = args
{ names = ["sort xs"]
, timeout = 0
, nMutants = 1000
, nTests = 1000
}
--, extraMutants = take 0
-- . concat
-- . lsmap (. sort)
-- $ cons2 (\y ys -> (++ (y:ys))) -- prepend non-empty list
-- \++/ cons2 (\y ys -> ((y:ys) ++)) -- append non-empty list
type Ty a = [a] -> [a]
main :: IO ()
main = do
as <- getArgsWith sargs
let run f = reportWith as f properties
case concat $ extra as of
"bool" -> run (sort :: Ty Bool)
"bools" -> run (sort :: Ty [Bool])
"int" -> run (sort :: Ty Int)
"i1" -> run (sort :: Ty Int1)
"i2" -> run (sort :: Ty Int2)
"i3" -> run (sort :: Ty Int3)
"w1" -> run (sort :: Ty Word1)
"w2" -> run (sort :: Ty Word2)
"w3" -> run (sort :: Ty Word3)
"unit" -> run (sort :: Ty ())
"" -> run (sort :: Ty Word2)
t -> putStrLn $ "unknown type " ++ t
-- This hack is only necessary when using sortCounter as a manual mutant
instance Bounded a => Bounded [a] where
minBound = []
maxBound = repeat maxBound -- non terminating upper bound
sortCounter :: (Bounded a, Ord a) => [a] -> [a]
sortCounter = (++ [maxBound]) . sort