moodymudskipper / nakedpipe

Pipe Into a Sequence of Calls Without Repeating the Pipe Symbol.
69 stars 7 forks source link

temporary variable assignment restricted to nakedpipe scope? #17

Closed daranzolin closed 4 years ago

daranzolin commented 4 years ago

Just thinking out loud, but I was experimenting with some alternative nested data patterns and thought it might be useful to be able to assign temporary variables restricted to the nakedpipe scope. For example, I wouldn't want cyl_data to enter my global environment here:

library(nakedpipe)
library(tibble)

mtcars %.% {
  split(.$cyl)
  ~~ . -> cyl_data
  lapply(., function(df) lm(mpg ~ wt, data = df))
  tibble(
    cyl = c(4, 6, 8),
    data = cyl_data, 
    model = .)
}

This might be too fringey and weird, but I would possibly write code like this in the future.

moodymudskipper commented 4 years ago

Hi David, do you have a syntax in mind? I wanted a way to save intermediate results conveniently so I don't think I want to change this behavior. I see how what you want is useful though.

What about :

~~ . -> (cyl_data) 

For your desired behavior? Does it appear intuitive enough?

daranzolin commented 4 years ago

I like ~~ . -> (cyl_data) a lot!

And yes, I agree, I wouldn't want to change the original behavior, as sometimes it is also useful to assign intermediary results to the global env. Sorry I wasn't more clear.

moodymudskipper commented 4 years ago

@daranzolin what do you think about using dotted variables when you don't want them stored in the calling env ?

We'd do ~~ . -> .cyl_data to store .cyl_data in a buffer environment, thus it'd be impossible to create a dotted variable in the calling environment but it seems like a fair limitation.

~~ . -> (cyl_data) would be more general and I like weird syntaxes but I'm afraid to confuse users further,

moodymudskipper commented 4 years ago

I've implemented the dotted version (and I have the code for the other too, but I don't think we'll need it).

The previous behavior remains:

library(nakedpipe)
library(tibble)

mtcars %.% {
  split(.$cyl)
  ~~ . -> cyl_data
  lapply(., function(df) lm(mpg ~ wt, data = df))
  tibble(
    cyl = c(4, 6, 8),
    data = cyl_data, 
    model = .)
}
#> # A tibble: 3 x 3
#>     cyl data                model       
#>   <dbl> <named list>        <named list>
#> 1     4 <df[,11] [11 x 11]> <lm>        
#> 2     6 <df[,11] [7 x 11]>  <lm>        
#> 3     8 <df[,11] [14 x 11]> <lm>
exists("cyl_data")
#> [1] TRUE

but using dotted variables make sures my calling environment stays clean

mtcars %.% {
  split(.$cyl)
  ~~ . -> .cyl_data
  lapply(., function(df) lm(mpg ~ wt, data = df))
  tibble(
    cyl = c(4, 6, 8),
    data = .cyl_data, 
    model = .)
}
#> # A tibble: 3 x 3
#>     cyl data                model       
#>   <dbl> <named list>        <named list>
#> 1     4 <df[,11] [11 x 11]> <lm>        
#> 2     6 <df[,11] [7 x 11]>  <lm>        
#> 3     8 <df[,11] [14 x 11]> <lm>
exists(".cyl_data")
#> [1] FALSE

I like it a lot in fact. Not only can we use intermediate temp variables, but we can also set temp variables at the start of the chain, and keep our code outside of it, looking forward to your feedback.

I still need to add tests, and mention in README and help files.

daranzolin commented 4 years ago

Perfection 👌 🙌 . I would absolutely use this syntax. What I love about nakedpipe is how it feels like something in between an anonymous function and regular procedural programming.

moodymudskipper commented 4 years ago

assignment to temp variables is documented and works with %D.%, it fails explicitly when trying to convert, because magrittr's environments don't permit it.

github-actions[bot] commented 2 years ago

This old thread has been automatically locked. If you think you have found something related to this, please open a new issue and link to this old issue if necessary.