Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

residual versions of map_ok et al #712

Closed
cdmistman opened this issue Jul 7, 2023 · 3 comments
Closed

residual versions of map_ok et al #712

cdmistman opened this issue Jul 7, 2023 · 3 comments

Comments

@cdmistman
Copy link

cdmistman commented Jul 7, 2023

it'd be really convenient if there was a version of map_ok that allowed the error type to be transformed via the Try traits. notably, blocked on rust-lang/rust#84277 but it might be possible to expose as a feature flag?

would be a shorthand for eg transforming an iter of io::Result to eyre::Result when calling a function that returns an eyre::Result on the ok value of io::Result.

std::iter::once(std::io::Result::Ok(()))
  .map(|res| eyre::Result::Ok(res?))
@Philippe-Cholet
Copy link
Member

Philippe-Cholet commented Jul 7, 2023

The problem I see is that you want eyre::Result while others could want anyhow::Result or other result types. I would also want to choose the HashMap type itertools use under the hood like ahash::AHashMap but others might prefer "fnv" or whatever.

Personally, solving "Advent of Code" in rust without much "unwrap/expect", I made a super trait named OkIterator on top of Iterator<Item=Result<T, E>> (with E: Into<anyhow::Error>) which convert results to the type I want under the hood, it's quite boilerplate though. Things like

fn ok_collect<B: FromIterator<T>>(self) -> anyhow::Result<B> {
    self.collect::<Result<_, _>>().map_err(Into::into)
}

There is also process_results which is a method in the latest version "0.11.0": std::iter::once(std::io::Result::Ok(())).process_results(|it| it.collect_vec()) (propage the error or map it).

EDIT: Maybe I'm just ignorant about "residual".

@cdmistman
Copy link
Author

Yeah, the type of the returned error should be generic. I used eyre as an example. I'm on mobile and only have a surface-level understanding of Try v2, but I suspect the type signature would look something like this:

trait Itertools {
  fn map_ok_residual<O1, O2, F, I>(self, f: F) -> I
  where
    Self: Iterator<Item = O1>,
    F: FnMut(<O1 as Try>::Output) -> O2,
    O1: Try,
    O2: Try + FromResidual<<O1 as Try>::Residual>,
    I: Iterator<Item = O2>;

Try v2 is currently feature-gated (linked in the original issue) so Try and FromResidual are only available on nightly. However an Iterator like this would be pretty convenient whether I want an eyre::Result, you want an anyhow::Result, or Alice wants a MyVeryOwnCustomStrangeResult

@Philippe-Cholet
Copy link
Member

Itertools currently uses "Rust stable" only.
Same as adding a dependency behind a feature flag, using nightly features (behind a feature flag or not) would increase the maintenance burden.
Here, if we were to ever use nightly, I think it would be to be able to specialize try_fold methods as it would allow to fasten multiple Iterator methods, just like we are working on fold specializations.
Therefore I feel confident in closing this, as not planned.

@Philippe-Cholet Philippe-Cholet closed this as not planned Won't fix, can't repro, duplicate, stale Oct 7, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants