X-Git-Url: http://git.megacz.com/?a=blobdiff_plain;f=GHC%2FList.lhs;h=689637e2ea42a52e077cc2ae8862e55b917efc0f;hb=30464c0cb915c2ae900909568fa8677bba341e45;hp=60fc90b2fb9ede137e9632e1b44f6e1ce1a005ac;hpb=f59ef9948524e4f7e3a947b89306ab377fd56849;p=haskell-directory.git diff --git a/GHC/List.lhs b/GHC/List.lhs index 60fc90b..689637e 100644 --- a/GHC/List.lhs +++ b/GHC/List.lhs @@ -111,12 +111,21 @@ null (_:_) = False -- | 'length' returns the length of a finite list as an 'Int'. -- It is an instance of the more general 'Data.List.genericLength', -- the result type of which may be any kind of number. -length :: [a] -> Int -length l = len l 0# - where - len :: [a] -> Int# -> Int - len [] a# = I# a# - len (_:xs) a# = len xs (a# +# 1#) +length :: [a] -> Int +length l = lenAcc 0# l + +{-# RULES +"length" [~1] forall xs. length xs = foldr incL (I# 0#) xs +"lenAcc" [1] forall n#. foldr incL (I# n#) = lenAcc n# + #-} + +incL :: a -> Int -> Int -- Internal +{-# NOINLINE [0] incL #-} +incL x n = n `plusInt` oneInt + +lenAcc :: Int# -> [a] -> Int -- Internal +lenAcc a# [] = I# a# +lenAcc a# (_:xs) = lenAcc (a# +# 1#) xs -- | 'filter', applied to a predicate and a list, returns the list of -- those elements that satisfy the predicate; i.e.,