on 45aa58f help sign in
elk/libraries/Array.elm
192 lines 5.4 kB history raw
1module Array where
3{-| A library for fast immutable arrays. The elements in an array must have the
4same type. The arrays are implemented in Relaxed Radix Balanced-Trees for fast
5reads, updates, and appends.
7# Creating Arrays
8@docs empty, repeat, initialize, fromList
10# Basics
11@docs length, equals, push, append
13# Get and Set
14@docs get, getMaybe, getWithDefault, set
16# Taking Arrays Apart
17@docs toList, toIndexedList, slice
19# Mapping and Folding
20@docs map, indexedMap, foldl, foldr
21-}
23import Native.Array
24import Basics (..)
25import Maybe (..)
26import List
28data Array a = Array
30{-| Initialize an array. `initialize n f` creates an array of length `n` with
31the element at index `i` initialized to the result of `(f i)`.
33 initialize 4 id == fromList [0,1,2,3]
34 initialize 4 (\n -> n*n) == fromList [0,1,4,9]
35 initialize 4 (always 0) == fromList [0,0,0,0]
36-}
37initialize : Int -> (Int -> a) -> Array a
38initialize = Native.Array.initialize
40{-| Creates an array with a given length, filled with a default element.
42 repeat 5 0 == fromList [0,0,0,0,0]
43 repeat 3 "cat" == fromList ["cat","cat","cat"]
45Notice that `repeat 3 x` is the same as `initialize 3 (always x)`.
46-}
47repeat : Int -> a -> Array a
48repeat n e = initialize n (always e)
50{-| Create an array from a list. -}
51fromList : [a] -> Array a
52fromList = Native.Array.fromList
54{-| Create a list of elements from an array.
56 toList (fromList [3,5,8]) == [3,5,8]
57-}
58toList : Array a -> [a]
59toList = Native.Array.toList
61-- TODO: make this a native function.
62{-| Create an indexed list from an array. Each element of the array will be
63paired with its index.
65 toIndexedList (fromList ["cat","dog"]) == [(0,"cat"), (1,"dog")]
66-}
67toIndexedList : Array a -> [(Int, a)]
68toIndexedList array =
69 List.zip [ 0 .. Native.Array.length array - 1 ] (Native.Array.toList array)
71{-| Apply a function on every element in an array.
73 map sqrt (fromList [1,4,9]) == fromList [1,2,3]
74-}
75map : (a -> b) -> Array a -> Array b
76map = Native.Array.map
78{-| Apply a function on every element with its index as first argument.
80 indexedMap (*) (fromList [5,5,5]) == fromList [0,5,10]
81-}
82indexedMap : (Int -> a -> b) -> Array a -> Array b
83indexedMap = Native.Array.indexedMap
85{-| Reduce an array from the left.
87 foldl (::) [] (fromList [1,2,3]) == [3,2,1]
88-}
89foldl : (a -> b -> b) -> b -> Array a -> b
90foldl = Native.Array.foldl
92{-| Reduce an array from the right.
94 foldr (+) 0 (repeat 3 5) == 15
95-}
96foldr : (a -> b -> b) -> b -> Array a -> b
97foldr = Native.Array.foldr
99{-| Return an empty array.
101 length empty == 0
102-}
103empty : Array a
104empty = Native.Array.empty
106{-| Check if all values of the array are equal. True if both arrays are the same
107length and the values are equal at every index.
109 equals (fromList [2,2]) (repeat 2 2) == True
110 equals (fromList [1,2]) (repeat 2 2) == False
111-}
112equals : Array a -> Array a -> Bool
113equals a b =
114 let go lists =
115 case lists of
116 (x::xs,y::ys) -> x == y && go (xs,ys)
117 ([],[]) -> True
118 _ -> False
119 in
120 go (Native.Array.toList a, Native.Array.toList b)
122{-| Push an element to the end of an array.
124 push 3 (fromList [1,2]) == fromList [1,2,3]
125-}
126push : a -> Array a -> Array a
127push = Native.Array.push
129{-| Return the element at the index. Breaks, if index is out of range. If the
130array length is unkown, use withDefaultGet oder getWithDefault.
132 get 2 (A.fromList [3,2,1]) == 1
133-}
134get : Int -> Array a -> a
135get = Native.Array.get
137{-| Return Just the element at the index or Nothing if the index is out of range.
139 getMaybe 2 (fromList [3,2,1]) == Just 2
140 getMaybe 5 (fromList [3,2,1]) == Nothing
141 getMaybe -1 (fromList [3,2,1]) == Nothing
142-}
143getMaybe : Int -> Array a -> Maybe a
144getMaybe i array =
145 if 0 <= i && i < Native.Array.length array
146 then Just (Native.Array.get i array)
147 else Nothing
149{-| Get the element at the index. If the index is out of range, the given default
150element is returned.
152 getWithDefault 0 2 (fromList [3,2,1]) == 1
153 getWithDefault 0 5 (fromList [3,2,1]) == 0
154-}
155getWithDefault : a -> Int -> Array a -> a
156getWithDefault default i array =
157 if 0 <= i && i < Native.Array.length array
158 then Native.Array.get i array
159 else default
161{-| Set the element at a particular index. Returns an updated array.
162If the index is out of range, the array is unaltered.
164 set 1 7 (fromList [1,2,3]) == fromList [1,7,3]
165-}
166set : Int -> a -> Array a -> Array a
167set = Native.Array.set
169{-| Slice an array given a range. The selection is inclusive, so the last
170element in the selection will also be in the new array. This may change in the
171future. You can select from the end by giving a negative Int.
173 slice 1 2 (fromList [0,1,2,3,4]) == fromList [1,2]
174 slice 1 -2 (fromList [0,1,2,3,4]) == fromList [1,2,3]
175 slice -3 -2 (fromList [0,1,2,3,4]) == fromList [2,3]
176-}
177slice : Int -> Int -> Array a -> Array a
178slice = Native.Array.slice
180{-| Return the length of an array.
182 length (fromList [1,2,3]) == 3
183-}
184length : Array a -> Int
185length = Native.Array.length
187{-| Append two arrays to a new one.
189 append (array 2 42) (array 3 81) == fromList [42,42,81,81,81]
190-}
191append : Array a -> Array a -> Array a
192append = Native.Array.append