fix f = f (fix f) -- f x = (x x) --type --data --newtype data FuzzyBoolean = CertainTrue | CertainFalse | Uncertain -- FuzzyBoolean - constructor de tip -- 3 constructori de date -- pot apărea în expresii fromFuzzy CertainTrue = True fromFuzzy CertainFalse = False fromFuzzy Uncertain = undefined -- construim un nou tip de date nou folosind constructori de bază. data Natural = Zero | Succ Natural deriving (Show, Eq) -- putem afișa la consolă și putem face == -- Zero -- constructor de date nular ~ valoare -- Succ -- constructor de date unar ~ funcție unu = Succ Zero doi = Succ unu --- important: vezi utilizare constructori de date în pattern-matching add n Zero = n add n (Succ m) = Succ $ add n m -- definire cu funcție de acces: data Natural2 = Zero2 | Succ2 { prev :: Natural2 } deriving Show -- prev îmi dă acces la valoarea pe care a fost apelat Succ2 unu' = Succ2 Zero2 doi' = Succ2 $ Succ2 Zero2 infixl 6 +* Zero2 +* n = n m +* n = Succ2 $ prev m +* n data MyMaybe a = MyNothing | MyJust { getJust :: a } data MultiTuplu a = Null | Single { get :: a } | Pair { fs :: a, sd :: a } | Triple { t1 :: a, t2 :: a, t3 :: a } deriving (Show, Eq) ones = 1 : ones --treeOnes = (1, treeOnes, treeOnes) -- tip recursiv data TreeInt = NodeInt { v :: Int, chd :: [TreeInt] } treeOnes = NodeInt 1 [treeOnes, treeOnes] -- v $ chd (chd treeOnes !! 0) !! 1 data Tree a = Nil | Leaf { val :: a } | Node { val :: a, copii :: [Tree a] } -- e.g. myTree = Node "radacina" [Node "copil1" [Leaf "frunza1", Leaf "frunza2"], Leaf "frunza3"] instance Show a => Show (Tree a) where show tree = pt 0 tree where pt level tree = case tree of Nil -> space level ++ "- \n" Leaf val -> space level ++ show val ++ "\n" Node val children -> space level ++ show val ++ "\n" ++ if all isNil children then "" else concatMap (pt $ level + 1) children space sp = [' ' | _ <- [1..sp * 2]] isNil Nil = True isNil _ = False preord :: Tree a -> [a] preord Nil = [] preord (Leaf x) = [x] preord (Node x children) = x : concatMap preord children treeB = build 1 where build n = Node n $ map build [2*n, 2*n+1] limit 0 t = Nil limit l t = case t of Node v ch -> Node v $ map (limit $ l - 1) ch _ -> t {- încercați la consolă limit 5 treeOnes limit 5 treeB take 10 $ preord treeB -- doar calea de pe partea stângă a arborelui, pentru că nu ne întoarcem niciodată preord $ limit 5 treeB -} -- definirea unui alias pentru un tip de date existent: type ListInt = [Integer] incList :: ListInt -> ListInt incList = map (+1) incTail = incList . tail tailIncTail = tail . incList . tail -- > :t incTail -- incTail :: ListInt -> [Integer] -- la sinteza de tip aliasul nu se propagă -- vezi tipul lui tailIncTail -- definirea unui alias pentru un tip de date existent, dar care -- se propagă pentru că este un tip de date de sine stătător, ca atunci când folosim data: newtype ListInt2 = List { getL :: [Integer] } deriving Show incList2 = List . map (+1) . getL incTail2 = incList2 . List . tail . getL -- observați tipul lui incTail2 în comparație cu incTail