Fork me on GitHub
#clojuredesign-podcast
<
2020-10-06
>
jumar06:10:42

I listened to the partition-by & group-by episode and one thing you mentioned is using partition-by for "splitting" a sequence into two portions. Wouldn't split-with be a more suitable for that purpose? https://stackoverflow.com/questions/64208708/replicate-java-peek-stream-method-in-clojure

nate17:10:07

Yes, if you know that you will only get two portions, then split-with would work as well

nate17:10:42

For split-with, you pass a predicate, and the collection is cut when that predicate goes from true to false For partition-by, you pass a function and a new partition is made every time the function returns a different value These can behave the same, if the partition-by function returns true and then false and the data is sorted conveniently:

(split-with #(< % 2) (range 5)) => [(0 1) (2 3 4)]
(partition-by #(< % 2) (range 5)) => [(0 1) (2 3 4)]
However, when the data isn't sorted, you get different results:
(split-with #(< % 2) [1 4 3 0 2]) => [(1) (4 3 0 2)]
(partition-by #(< % 2) [1 4 3 0 2]) => ((1) (4 3) (0) (2))

bocaj14:10:36

Looks like it depends on which data structure you're using, and laziness. Stackoverflow question was specifically about a side effect, so I think maybe they could use a queue instead of a list. I'm curious as well about the difference.

nate17:10:42

For split-with, you pass a predicate, and the collection is cut when that predicate goes from true to false For partition-by, you pass a function and a new partition is made every time the function returns a different value These can behave the same, if the partition-by function returns true and then false and the data is sorted conveniently:

(split-with #(< % 2) (range 5)) => [(0 1) (2 3 4)]
(partition-by #(< % 2) (range 5)) => [(0 1) (2 3 4)]
However, when the data isn't sorted, you get different results:
(split-with #(< % 2) [1 4 3 0 2]) => [(1) (4 3 0 2)]
(partition-by #(< % 2) [1 4 3 0 2]) => ((1) (4 3) (0) (2))

nate17:10:22

I also think it's interesting that split-with returns a vector (eager) of two lazy sequences, so they are computed as you consume them