purescript-lists icon indicating copy to clipboard operation
purescript-lists copied to clipboard

Add foldlWhile to List.Lazy

Open drewolson opened this issue 6 years ago • 16 comments

I'm not sure if this is something you'd like to add, but I've found this construct useful in other languages that support explicit lazy lists.

For example, both rust and elixir support something like this function.

drewolson avatar Feb 26 '19 04:02 drewolson

Any thoughts on this one @garyb?

drewolson avatar Mar 01 '19 14:03 drewolson

It seems sensible enough to me! I don't really have much of a personal opinion about the Lazy stuff here, since I haven't needed it much.

@hdgarrood / @natefaubion any thoughts?

garyb avatar Mar 08 '19 17:03 garyb

Yeah, seems fine! No strong opinions either way from me. I don't think I've ever used lazy lists in PureScript :open_mouth:

hdgarrood avatar Mar 08 '19 17:03 hdgarrood

Is there a reason to not also add such a function for Data.List? I don't like having API differences between the two unless there's a good reason.

natefaubion avatar Mar 08 '19 17:03 natefaubion

Also, isn't this foldl with the arguments flipped?

natefaubion avatar Mar 08 '19 17:03 natefaubion

Oh yeah of course, this is folding from the left, so I guess it should be called foldlWhile?

hdgarrood avatar Mar 08 '19 18:03 hdgarrood

I think we should rename it, and flip the arguments back then.

natefaubion avatar Mar 08 '19 18:03 natefaubion

~~Actually, on second thoughts I'm no longer sure which direction it's folding in.~~ Yes, this is definitely a left fold; see https://stackoverflow.com/questions/13280159/haskell-foldl-and-foldr/13280185

hdgarrood avatar Mar 08 '19 18:03 hdgarrood

@hdgarrood my understanding was that folds over lazy lists were almost by definition folds from the right. I'm no expert, though. I'm happy to do any of the following:

  • rename to foldrWhile and swap the args
  • also add a version of the function to List

Let me know.

drewolson avatar Mar 10 '19 14:03 drewolson

@drewolson What determines left or right fold is just associativity of the operations, and this is left associative. For it to be right associative you would need to pass in the accumulator for the entire tail to the folding function. A lazy foldr obviates the need for a breaker because you have control over evaluation of the tail when folding. Since evaluation of the tail is deferred, if you never demand it, it's never run, letting you short circuit the computation.

I would like both of those tasks to be done: changing the name/signature, and adding an implementation for Data.List so we can keep API parity.

natefaubion avatar Mar 10 '19 15:03 natefaubion

@hdgarrood @natefaubion I believe I've addressed all concerns. Thanks for all the feedback!

drewolson avatar Mar 10 '19 15:03 drewolson

I'd prefer to keep the internal go function, since a) it means that we won't need to rebind f on each loop, and b) it makes it a little easier to read as you no longer have to worry about f changing.

hdgarrood avatar Mar 13 '19 16:03 hdgarrood

@hdgarrood I actually found the indirection of introducing go made the code harder for me to read. That said, if the consensus is that I should re-introduce it, I'm happy to do so.

drewolson avatar Mar 18 '19 14:03 drewolson

Any further thoughts on this? If it isn't something that folks are interested in, I'm happy to close the PR.

drewolson avatar Apr 07 '19 19:04 drewolson

It's not that we don't want it, it's just that we're spread fairly thin. I'm more focused on the upcoming 0.12.4 compiler release right now.

hdgarrood avatar Apr 07 '19 19:04 hdgarrood

@hdgarrood totally understood. No rush from my end, just didn't want to leave it hanging around if it was cruft. Appreciate the response!

drewolson avatar Apr 07 '19 19:04 drewolson