myrrlyn / tap

Generic extensions for tapping values in Rust.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

add pipe_if method(s)

Zoybean opened this issue · comments

Reading this comment on the rust internals forum got me interested in a conditional pipe method; to borrow the example from the post, it would simplify pipes with basic tests like this:

Builder::new()
    .foo()
    .bar()
    .pipe(|it| if bazable {
        it.baz()
    } else {
        it
    })
    .quux()
    .build()

Into this:

Builder::new()
    .foo()
    .bar()
    .pipe_if(bazable, |it| it.baz())
    .quux()
    .build()

I figure the implementations would be trivial, the main factor that I see getting in the way of this is that it could mean doubling the number of methods on Pipe, by adding _ref, _ref_mut, _deref etc variants.

I think that would be great : )

Also something like pipe_map:

Builder::new()
    .foo()
    .bar()
    .pipe(|it| if let Some(inner) = maybe_baz {
        it.baz(inner)
    } else {
        it
    })
    .quux()
    .build()

Builder::new()
    .foo()
    .bar()
    .pipe_map(maybe_baz, |it, inner| it.baz(inner))
    .quux()
    .build()

pub trait Pipe {
    ...

    #[inline(always)]
    fn pipe_map<O>(self, option: Option<O>, func: impl FnOnce(Self, O) -> Self) -> Self
    where
        Self: Sized,
        O: Sized,
    {
        if let Some(inner) = option {
            func(self, inner)
        } else {
            self
        }
    }
}