Paste: Map values only conditionally

Author: nomennescio
Mode: factor
Date: Fri, 5 Aug 2022 16:03:53
Plain Text |
Both `filter-map` and `map-filter` use two quotes to filter and map at the same time. That requires recalculation of the new value and the condition, while it often happens you want to have the condition depend on the new value. Therefore you want a single quotation that has both the new value and the condition.

I wrote map-if for that, any comments?

: map-if ( ... seq quot: ( ... elt -- ... newelt ? ) -- ... newseq ) V{ } clone [ [ swap [ push ] [ 2drop ] if ] curry compose each ] keep ; inline

Annotation: Usage

Author: nomennescio
Mode: factor
Date: Fri, 5 Aug 2022 16:08:50
Plain Text |
{ 2 3 4 } [ 2 * dup 6 = ] map-if
{ 6 }

Annotation: Usage

Author: nomennescio
Mode: factor
Date: Fri, 5 Aug 2022 16:11:18
Plain Text |
{ 10 12 14 } [ 2/ dup odd? ] map-if
{ 5 7 }

Annotation: Alternate form with fry

Author: nomennescio
Mode: factor
Date: Fri, 5 Aug 2022 16:16:11
Plain Text |
: map-if ( ... seq quot: ( ... elt -- ... newelt ? ) -- ... newseq ) V{ } clone [ '[ @ _ swap [ push ] [ 2drop ] if ] each ] keep ; inline

Annotation: Alternate names

Author: nomennescio
Mode: factor
Date: Fri, 5 Aug 2022 16:42:50
Plain Text |
atax1a suggested `map-sift` for `map-if`, to allude to `sift` (which technically would require
map-sift ( seq quot: ( elt -- newelt/f ) -- newseq )

erg mentioned that the `-if` might allude to a partition, and maybe use `-when` instead.

I think the `map-sift` is nicer and closely alludes to a map followed by a (modified) sift. To accommodate for variants, I propose the following two names, but `map-if*` might not be needed at all

: map-sift ( ... seq quot: ( ... elt -- ... newelt ? ) -- ... newseq ) 
: map-sift* ( ... seq quot: ( ... elt -- ... newelt/f ) -- ... newseq ) 

New Annotation

Summary:
Author:
Mode:
Body: