> On Tue, Feb 5, 2019 at 11:05 PM ToddAndMargo via perl6-users
> <perl6-users@perl.org> wrote:
>>
>> Hi All,
>>
>> What is with the starting ending Nils?  There are only four
>> elements, why now six?
>>
>> And how to I correct this?
>>
>> $ p6 'my Str $x="abcd";
>>        for split( "",@$x ).kv -> $i,$j {
>>        say "Index <$i> = <$j> = ord <" ~ ord($j) ~ ">";}'
>>
>> Use of Nil in string context
>>     in block  at -e line 1
>> Index <0> = <> = ord <>         <----------------- nil ???
>> Index <1> = <a> = ord <97>
>> Index <2> = <b> = ord <98>
>> Index <3> = <c> = ord <99>
>> Index <4> = <d> = ord <100>
>> Use of Nil in string context
>>     in block  at -e line 1
>> Index <5> = <> = ord <>         <----------------- nil ???
>>
>>
>> Many thanks,
>> -T

On 2/6/19 5:19 AM, Brad Gilbert wrote:
The reason there is a Nil, is you asked for the ord of an empty string.

     "".ord =:= Nil

The reason there are two empty strings is you asked for them.

When you split with "", it will split on every character boundary,
which includes before the first character, and after the last.
That's literally what you asked for.

     my Str $x = "abcd";
     say split( "", $x ).perl;
     # ("", "a", "b", "c", "d", "").Seq

Perl6 doesn't treat this as a special case like other languages do.
You basically asked for this:

     say split( / <after .> | <before .> /, $x ).perl;
     # ("", "a", "b", "c", "d", "").Seq

Perl6 gave you what you asked for.

That is actually useful btw:

     say split( "", "abcd" ).join("|");
     # |a|b|c|d|

You should be using `comb` if you want a list of characters not `split`.

     # these are all identical
     'abcd'.comb.kv
     'abcd'.comb(1).kv
     comb( 1, 'abcd' ).kv

Also why did you add a pointless `@` to `$x` ?
(Actually I'm fairly sure I know why.)


Hi Brad,

Thank you!

So it is a "feature" of split.  Split sees the non-existent
index before the start and the non-existent index after
the end as something.  Mumble. Mumble.

To answer you question about the stray "@".  I forgot
to remove it.

But it brings up an inconsistency in Perl 6.

This works and also is the source of the stay "@" I forgot
to remove from the split example.


$ p6 'my Buf $x=Buf.new(0x66,0x61,0x62,0x63); for @$x.kv -> $i, $j {say "Index <$i> = <$j> = chr <" ~ chr($j) ~ ">";}'

Index <0> = <102> = chr <f>
Index <1> = <97> = chr <a>
Index <2> = <98> = chr <b>
Index <3> = <99> = chr <c>



So, this should also work, but does not:

$ p6 'my Str $x="abcd"; for @$x.kv -> $i, $j {say "Index <$i> = <$j> = ord <" ~ ord($j) ~ ">";}'

Index <0> = <abcd> = ord <97>


Strings only have one index (0) and why we have the substr command.

$ p6 'my Str $x="abcd"; say $x[0];'
abcd


So all the rules for other arrays go out the window for
a Str.  A string is an array of one cell.  And if I
truly want an array of characters, I need to use Buf
and not Str.  Only problem is that Str has all the cool
tools.

-T

Reply via email to