Re: [perl #61130] :nth() does not work with :x() or :g in .subst in Rakudo

2008-12-08 Thread Patrick R. Michaud
On Sun, Dec 07, 2008 at 03:09:30PM -0800, Moritz Lenz via RT wrote:
> > ...but not :x() together with :nth()...
> > 
> > $ perl6 -e 'say "foo1foo2foo3foo4".subst("foo", "bar", :x(2),
> > :nth(2))' # expected foo1bar2foo3bar4
> > foo1bar2foo3foo4
> > 
> > The above are my personal expectations. The current version of S05 is
> > silent on how :nth() interacts with :x() and :g. There are spectests
> > for :g:nth but not (as far as I can see) for :x:nth.
> 
> Since your personal expectations are the same as mine, I took the liberty to
> turn our expectations into spec tests, in
> t/spec/S05-substitution/subst.t (pugs r24207).
> 
> The reasoning behind it is quite simple: I imagine :g to mean the same as
> :x(*). Now a :x($x) and :nth($n) interact like this:
> 
> for 1 .. $x {
> match here
> if ($x-1) % $n == 0 {
> do substitution
> }
> }
> 
> (CC'ing p6l, since it defines language semantics, albeit just a bit)

The problem with this reasoning is that :nth doesn't have to be an 
integer -- S05 also allows things like

:nth(1,2,3,5,8,13)
:nth({.is_fibonacci})

It's not immediately obvious how those forms of :nth would interact 
with :x or :g.

The way to do something like "replace every 3rd occurrence" would
seem to be to do things like:

:nth({ $_ % 3 == 0 })
:nth(3..*:by(3))

Another problem is that :x($n) specifies "perform $n substitutions",
such that if we say :x(4) and there aren't four things to substitute,
then none of the substitutions take place.

At the moment I think that :x specifies a constraint on the
total number of substitutions that are (must be) performed,
while :nth selects the candidate matches to be substituted.
Thus

.subst( $pat, $rep, :nth(1,4,9,16,25,36), :x(4) )

would perform substitutions on the 1st, 4th, 9th, and 16th matches,
and do nothing if at least sixteen matches were not found.

Pm


[perl #61130] :nth() does not work with :x() or :g in .subst in Rakudo

2008-12-08 Thread Moritz Lenz via RT
On Sun Dec 07 07:24:07 2008, masak wrote:
> The .subst method in Rakudo r33599 can understand :x()...
> 
> $ perl6 -e 'say "foo1foo2foo3foo4".subst("foo", "bar", :x(2))' # yes
> bar1bar2foo3foo4
> 
> ...and :nth()...
> 
> $ perl6 -e 'say "foo1foo2foo3foo4".subst("foo", "bar", :nth(2))' # yes
> foo1bar2foo3foo4
> 
> ...and :g...
> 
> $ perl6 -e 'say "foo1foo2foo3foo4".subst("foo", "bar", :g)' # yes
> bar1bar2bar3bar4
> 
> ...but not :x() together with :nth()...
> 
> $ perl6 -e 'say "foo1foo2foo3foo4".subst("foo", "bar", :x(2),
> :nth(2))' # expected foo1bar2foo3bar4
> foo1bar2foo3foo4
> 
> ...and not :g together with :nth().
> 
> $ perl6 -e 'say "foo1foo2foo3foo4".subst("foo", "bar", :g, :nth(2))' #
> expected foo1bar2foo3bar4
> foo1bar2foo3foo4
> 
> The above are my personal expectations. The current version of S05 is
> silent on how :nth() interacts with :x() and :g. There are spectests
> for :g:nth but not (as far as I can see) for :x:nth.

Since your personal expectations are the same as mine, I took the liberty to
turn our expectations into spec tests, in
t/spec/S05-substitution/subst.t (pugs r24207).

The reasoning behind it is quite simple: I imagine :g to mean the same as
:x(*). Now a :x($x) and :nth($n) interact like this:

for 1 .. $x {
match here
if ($x-1) % $n == 0 {
do substitution
}
}

(CC'ing p6l, since it defines language semantics, albeit just a bit)