Skip to content

Note about semantics of (!!) is not specific enough, if it's correct

The definition of (!!) in GHC.List, copied below, has a vague note about semantics for the Prelude and HBC versions being different. I can't see the difference myself. If there really is a difference, the details should be in the comment.

-- | List index (subscript) operator, starting from 0.
-- It is an instance of the more general 'Data.List.genericIndex',
-- which takes an index of any integral type.
(!!)                    :: [a] -> Int -> a
#ifdef USE_REPORT_PRELUDE
xs     !! n | n < 0 =  error "Prelude.!!: negative index"
[]     !! _         =  error "Prelude.!!: index too large"
(x:_)  !! 0         =  x
(_:xs) !! n         =  xs !! (n-1)
#else
-- HBC version (stolen), then unboxified
-- The semantics is not quite the same for error conditions
-- in the more efficient version.
--
xs !! (I# n0) | isTrue# (n0 <# 0#) =  error "Prelude.(!!): negative index\n"
              | otherwise          =  sub xs n0
                         where
                            sub :: [a] -> Int# -> a
                            sub []     _ = error "Prelude.(!!): index too large\n"
                            sub (y:ys) n = if isTrue# (n ==# 0#)
                                           then y
                                           else sub ys (n -# 1#)
#endif
Trac metadata
Trac field Value
Version 7.9
Type Bug
TypeOfFailure OtherFailure
Priority normal
Resolution Unresolved
Component libraries/base
Test case
Differential revisions
BlockedBy
Related
Blocking
CC ekmett, hvr
Operating system
Architecture
To upload designs, you'll need to enable LFS and have an admin enable hashed storage. More information