Skip to content

Commit c7ed1b9

Browse files
Expand data/list
1 parent b46d28c commit c7ed1b9

File tree

3 files changed

+243
-17
lines changed

3 files changed

+243
-17
lines changed

hackett-doc/scribblings/hackett/reference.scrbl

Lines changed: 172 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -712,6 +712,22 @@ error, and if @racket[xs] is infinitely long, @racket[init!] will never return.
712712
(init! {1 :: 2 :: 3 :: Nil})
713713
(eval:error (init! (: Nil (t:List t:Integer)))))}
714714

715+
@defproc[(inits [xs (t:List a)]) (t:List (t:List a))]{
716+
717+
Returns a list of the inital segments of @racket[xs].
718+
719+
@(hackett-examples
720+
(inits {1 :: 2 :: 3 :: Nil})
721+
(inits (: Nil (t:List t:Integer))))}
722+
723+
@defproc[(tails [xs (t:List a)]) (t:List (t:List a))]{
724+
725+
Returns a list of the terminal segments of @racket[xs].
726+
727+
@(hackett-examples
728+
(tails {1 :: 2 :: 3 :: Nil})
729+
(tails (: Nil (t:List t:Integer))))}
730+
715731
@defproc[(uncons [xs (t:List a)]) (t:Maybe (t:Tuple a (t:List a)))]{
716732

717733
When @racket[xs] is @racket[Nil], @racket[uncons xs] is @racket[Nothing]. Otherwise, if @racket[xs]
@@ -757,6 +773,16 @@ Produces a list with the first @racket[n] elements of @racket[xs]. If @racket[xs
757773
(take 2 {1 :: Nil})
758774
(take 2 (: Nil (t:List t:Integer))))}
759775

776+
@defproc[(take-while [p {a t:-> t:Bool}] [xs (t:List a)]) (t:List a)]{
777+
778+
Returns the longest initial segment of @racket[xs] such that every element satisfies @racket[p].
779+
780+
@(hackett-examples
781+
(take-while (λ [x] {(remainder! x 2) == 1}) {1 :: 3 :: 6 :: 9 :: Nil})
782+
(let ([is-just (maybe False (const True))])
783+
(take-while is-just {(Just 1) :: (Just 2) :: Nothing :: (Just 3) :: Nil}))
784+
(take-while (λ [x] {(remainder! x 2) == 0}) (: Nil (t:List t:Integer))))}
785+
760786
@defproc[(drop [n t:Integer] [xs (t:List a)]) (t:List a)]{
761787

762788
Produces a list like @racket[xs] without its first @racket[n] elements. If @racket[xs] contains fewer
@@ -767,6 +793,69 @@ then @racket[n] elements, the result is @racket[Nil].
767793
(drop 2 {1 :: Nil})
768794
(drop 2 (: Nil (t:List t:Integer))))}
769795

796+
@defproc[(drop-while [p {a t:-> t:Bool}] [xs (t:List a)]) (t:List a)]{
797+
798+
Returns the longest terminal segment of @racket[xs] which is either @racket[Nil] or starts with an
799+
element @racket[x] such that @racket[(not (p x))].
800+
801+
@(hackett-examples
802+
(drop-while (λ [x] {(remainder! x 2) == 1}) {1 :: 3 :: 6 :: 9 :: Nil})
803+
(let ([is-just (maybe False (const True))])
804+
(drop-while is-just {(Just 1) :: (Just 2) :: Nothing :: (Just 3) :: Nil}))
805+
(drop-while (λ [x] {(remainder! x 2) == 0}) (: Nil (t:List t:Integer))))}
806+
807+
@defproc[(nth [xs (t:List a)] [n t:Integer]) (t:Maybe a)]{
808+
809+
Returns @racket[Just] the nth element of @racket[xs] if it exists, starting at 0, and
810+
@racket[Nothing] if it doesn't.
811+
812+
@(hackett-examples
813+
(nth {1 :: 2 :: 3 :: Nil} 2)
814+
(nth {1 :: 2 :: 3 :: Nil} -1)
815+
(nth {1 :: Nil} 2)
816+
(nth (: Nil (t:List t:Integer)) 2))}
817+
818+
@defproc[(nth! [xs (t:List a)] [n t:Integer]) a]{
819+
820+
Returns the nth element of @racket[xs], starting at 0. This function is
821+
@tech[#:key "partial function"]{partial}, because it errors when @racket[{n >= (length xs)}].
822+
823+
@(hackett-examples
824+
(nth! {1 :: 2 :: 3 :: Nil} 2)
825+
(eval:error (nth! {1 :: 2 :: 3 :: Nil} -1))
826+
(eval:error (nth! {1 :: Nil} 2))
827+
(eval:error (nth! (: Nil (t:List t:Integer)) 2)))}
828+
829+
@defproc[(find-index [p {a t:-> Bool}] [xs (t:List a)]) (t:Maybe t:Integer)]{
830+
831+
Finds the first element of @racket[xs] which satisfies @racket[p], and returns @racket[Just] its
832+
index. If there is no such element, the function returns @racket[Nothing].
833+
834+
@(hackett-examples
835+
(find-index (λ [x] {(remainder! x 2) == 0}) {1 :: 2 :: 3 :: Nil})
836+
(find-index (λ [x] {x < 0}) {1 :: 2 :: 3 :: Nil})
837+
(find-index (const True) (: Nil (t:List t:Integer))))}
838+
839+
@defproc[(index-of [_ (Eq a)] [x a] [xs (t:List a)]) (t:Maybe t:Integer)]{
840+
841+
Finds the first occurrence of @racket[x] in @racket[xs] and returns @racket[Just] its index. If
842+
@racket[x] is not contained in @racket[xs], the function returns @racket[Nothing]. This is
843+
equivalent to @racket[(find-index (== x) xs)].
844+
845+
@(hackett-examples
846+
(index-of 2 {1 :: 2 :: 3 :: Nil})
847+
(index-of -1 {1 :: 2 :: 3 :: Nil})
848+
(index-of 2 Nil))}
849+
850+
@defproc[(find [p {a t:-> t:Bool}] [xs (t:List a)]) (t:Maybe a)]{
851+
852+
Returns @racket[Just] the first element @racket[_x] of @racket[xs] such that @racket[(p _x)] is
853+
@racket[True]. If no element in @racket[xs] satisfies @racket[p], @racket[Nothing] is returned.
854+
855+
@(hackett-examples
856+
(find (λ [x] {x > 5}) {3 :: 7 :: 2 :: 9 :: 12 :: 4 :: Nil})
857+
(find (λ [x] {x > 5}) {1 :: 2 :: 3 :: Nil}))}
858+
770859
@defproc[(filter [f {a t:-> t:Bool}] [xs (t:List a)]) (t:List a)]{
771860

772861
Produces a list that contains each element, @racket[_x], for which @racket[_x] is an element of
@@ -808,6 +897,37 @@ the following expression:
808897
(foldl * 1 {1 :: 2 :: 3 :: 4 :: 5 :: Nil})
809898
(foldl - 0 {1 :: 2 :: 3 :: 4 :: 5 :: Nil}))}
810899

900+
@defproc[(unfoldr [step {b t:-> (t:Maybe (t:Tuple a b))}] [seed b]) (t:List a)]{
901+
902+
@racket[unfoldr] constructs a list from an initial value, stopping when @racket[(step seed)] is
903+
@racket[Nothing]. In a certain way, @racket[unfoldr] acts as a dual to @racket[foldr]. More
904+
specifically, @racket[{(unfoldr g (foldr f z xs)) == xs}] when @racket[{(g z) == Nothing}] and
905+
@racket[{(g (f x y)) == (Just (tuple x y))}] for any @racket[x] in @racket[xs].
906+
907+
@(hackett-examples
908+
(unfoldr (λ [x] (if {x == 1} Nothing
909+
(Just (Tuple (show x) (quotient! x 2)))))
910+
128)
911+
(take 5 (unfoldr (λ [x] (Just (Tuple x {x + 2}))) 0)))}
912+
913+
@defproc[(concat [_ (Monoid m)] [ms (t:List m)]) m]{
914+
Returns the result of appending each element of @racket[ms] together. Equivalent to
915+
@racket[(foldr ++ mempty)].
916+
917+
@(hackett-examples
918+
(eval:check (concat {"a" :: "b" :: "c" :: Nil}) "abc")
919+
(eval:check (concat {{1 :: Nil} :: {2 :: 3 :: Nil} :: {4 :: 5 :: 6 :: Nil} :: Nil})
920+
(:: 1 (:: 2 (:: 3 (:: 4 (:: 5 (:: 6 Nil))))))))}
921+
922+
@defproc[(fold-map [_ (Monoid m)] [f {a t:-> m}] [xs (List a)]) m]{
923+
924+
Applies @racket[f] to each element of @racket[xs] and concatenates each resulting list. Equivalent
925+
to @racket[=<<] when @racket[m] is @racket[(List b)] for some @racket[b].
926+
927+
@(hackett-examples
928+
(fold-map show {1 :: 2 :: 3 :: Nil})
929+
(fold-map tail {{1 :: Nil} :: Nil :: {2 :: 3 :: Nil} :: {4 :: 5 :: 6 :: Nil} :: Nil}))}
930+
811931
@defproc[(sum [xs (t:List t:Integer)]) t:Integer]{
812932

813933
Adds the elements of @racket[xs] together and returns the sum. Equivalent to @racket[(foldl + 0)].
@@ -816,6 +936,23 @@ Adds the elements of @racket[xs] together and returns the sum. Equivalent to @ra
816936
(eval:check (sum {1 :: 2 :: 3 :: Nil}) 6)
817937
(eval:check (sum Nil) 0))}
818938

939+
@defproc[(product [xs (t:List t:Integer)]) t:Integer]{
940+
941+
Multiplies the elements of @racket[xs] together and returns the product. Equivalent to
942+
@racket[(foldl * 1)].
943+
944+
@(hackett-examples
945+
(eval:check (product {1 :: 2 :: 3 :: 4 :: Nil}) 24)
946+
(eval:check (product Nil) 1))}
947+
948+
@defproc[(iterate [step {a t:-> a}] [seed a]) (List a)]{
949+
950+
Returns the infinite list @racket[{seed :: (step seed) :: (step (step seed)) :: ...}].
951+
952+
@(hackett-examples
953+
(take 5 (iterate (+ 1) 0))
954+
(take 5 (iterate (λ [x] {x ++ "a"}) "")))}
955+
819956
@defproc[(reverse (xs (t:List a))) (t:List a)]{
820957

821958
Returns @racket[xs] in reversed order.
@@ -828,7 +965,7 @@ Returns @racket[xs] in reversed order.
828965

829966
This function will apply @racket[f] to each element in @racket[as] and @racket[bs] until it
830967
has reached the end of either, then it returns a list like
831-
@racket[{f _a0 _b0 :: f _a1 _b1 :: f _a2 _b2 :: ... :: Nil}] (where @racket[as] contains
968+
@racket[{(f _a0 _b0) :: (f _a1 _b1) :: (f _a2 _b2) :: ... :: Nil}] (where @racket[as] contains
832969
elements named @racket[_a0], @racket[_a1], @racket[_a2] etc., and @racket[bs] contains elements
833970
named @racket[_b0], @racket[_b1], @racket[_b2] etc.).
834971

@@ -857,11 +994,18 @@ Returns an infinite list containing only @racket[x].
857994
@(hackett-examples
858995
(take 5 (repeat 1)))}
859996

997+
@defproc[(replicate [n Integer] [x a]) (t:List a)]{
998+
999+
Returns a list of @racket[n] copies of @racket[x].
1000+
1001+
@(hackett-examples
1002+
(replicate 3 1))}
1003+
8601004
@defproc[(cycle! [xs (t:List a)]) (t:List a)]{
8611005

8621006
Returns the infinite list @racket[{xs ++ xs ++ xs ++ ...}]. If @racket[xs] is infinite,
863-
@racket[cycle! xs == xs]. This function is @tech[#:key "partial function"]{partial},
864-
because it errors when given @racket[Nil].
1007+
@racket[{(cycle! xs)or == xs}]. This function is @tech[#:key "partial function"]{partial}, because it
1008+
errors when given @racket[Nil].
8651009

8661010
@(hackett-examples
8671011
(take 10 (cycle! {1 :: 2 :: 3 :: Nil}))
@@ -871,8 +1015,8 @@ because it errors when given @racket[Nil].
8711015

8721016
Logically ors the elements of @racket[xs] together and returns the result. Equivalent to @racket[(foldr || False)].
8731017
Because it uses a right fold, the only elements which will be evaluated are those before the first expression which
874-
evaluates to @racket[True]. Additionally, @racket[or infinite-list] can never return @racket[False], and
875-
@racket[or (repeat False)] will never terminate.
1018+
evaluates to @racket[True]. Additionally, @racket[(or infinite-list)] can never return @racket[False], and
1019+
@racket[(or (repeat False))] will never terminate.
8761020

8771021
@(hackett-examples
8781022
(or {True :: False :: Nil})
@@ -884,8 +1028,8 @@ evaluates to @racket[True]. Additionally, @racket[or infinite-list] can never re
8841028

8851029
Logically ands the elements of @racket[xs] together and returns the result. Equivalent to @racket[(foldr && True)].
8861030
Because it uses a right fold, the only elements which will be evaluated are those before the first expression which
887-
evaluates to @racket[False]. Additionally, @racket[and infinite-list] can never return @racket[True], and
888-
@racket[and (repeat True)] will never terminate.
1031+
evaluates to @racket[False]. Additionally, @racket[(and infinite-list)] can never return @racket[True], and
1032+
@racket[(and (repeat True))] will never terminate.
8891033

8901034
@(hackett-examples
8911035
(and {True :: False :: Nil})
@@ -947,6 +1091,7 @@ in @racket[xs] will be checked for equality.
9471091

9481092
@(hackett-examples
9491093
(delete 2 {1 :: 2 :: 3 :: Nil})
1094+
(delete 2 {1 :: 2 :: 3 :: 2 :: Nil})
9501095
(delete 0 {1 :: 2 :: 3 :: Nil})
9511096
(head (delete 1 {1 :: 2 :: (error! "never happens") :: Nil}))
9521097
(delete 1 Nil))}
@@ -960,13 +1105,14 @@ such @racket[y] will be checked for equality.
9601105
@(hackett-examples
9611106
(delete-by > 2 {1 :: 2 :: 3 :: Nil})
9621107
(delete-by > 0 {1 :: 2 :: 3 :: Nil})
963-
(head (delete-by not= 1 {1 :: 2 :: (error! "never happens") :: Nil}))
1108+
(head (delete-by /= 1 {1 :: 2 :: (error! "never happens") :: Nil}))
9641109
(delete-by (λ [y x] {(remainder! y x) == 0}) 2 Nil)
9651110
(delete-by (error! "never happens") (error! "never happens") (: Nil (t:List t:Integer))))}
9661111

9671112
@defproc[(intersperse [x a] [xs (t:List a)]) (t:List a)]{
9681113

969-
Given a separator and a list, intersperse intersperses the separator between each element of the list.
1114+
Given a separator and a list, intersperse returns a new list with the separator placed between each
1115+
element of the list.
9701116

9711117
@(hackett-examples
9721118
(intersperse 42 {1 :: 2 :: 3 :: Nil})
@@ -1035,9 +1181,14 @@ evaluated, produces the value.
10351181
@subsection[#:tag "reference-equality"]{Equality}
10361182

10371183
@defclass[(t:Eq a)
1038-
[== {a t:-> a t:-> t:Bool}]]{
1184+
[== {a t:-> a t:-> t:Bool}]
1185+
[/= {a t:-> a t:-> t:Bool}]]{
10391186
The class of types with a notion of equality. The @racket[==] method should produce @racket[True] if
1040-
both of its arguments are equal, otherwise it should produce @racket[False].
1187+
both of its arguments are equal, otherwise it should produce @racket[False]. The @racket[/=]
1188+
method should produce @racket[True] if its arguments are unequal, otherwise it should produce
1189+
@racket[False]. Default implementations of @racket[==] and @racket[/=] are given in terms of the
1190+
negation of the other, in case inequality is easier to define than equality, or if it is more
1191+
efficient to implement independent definitions for each.
10411192

10421193
@defmethod[== {a t:-> a t:-> t:Bool}]{
10431194

@@ -1046,7 +1197,16 @@ both of its arguments are equal, otherwise it should produce @racket[False].
10461197
(eval:check {10 == 11} False)
10471198
(eval:check {{1 :: 2 :: Nil} == {1 :: 2 :: Nil}} True)
10481199
(eval:check {{1 :: 2 :: Nil} == {1 :: Nil}} False)
1049-
(eval:check {{1 :: 2 :: Nil} == {1 :: 3 :: Nil}} False))}}
1200+
(eval:check {{1 :: 2 :: Nil} == {1 :: 3 :: Nil}} False))}
1201+
1202+
@defmethod[/= {a t:-> a t:-> t:Bool}]{
1203+
1204+
@(hackett-examples
1205+
(eval:check {10 /= 10} False)
1206+
(eval:check {10 /= 11} True)
1207+
(eval:check {{1 :: 2 :: Nil} /= {1 :: 2 :: Nil}} False)
1208+
(eval:check {{1 :: 2 :: Nil} /= {1 :: Nil}} True)
1209+
(eval:check {{1 :: 2 :: Nil} /= {1 :: 3 :: Nil}} True))}}
10501210

10511211
@subsection[#:tag "reference-semigroup-monoid"]{Semigroups and monoids}
10521212

0 commit comments

Comments
 (0)