Bug somewhere in :put/map/range/lambda functions?

8 views
Skip to first unread message

Tim Chase

unread,
Jan 9, 2021, 2:27:19 PM1/9/21
to v...@vim.org
Tried this:

:put=range(1,10)

and it worked as expected, appending the numbers 1..10 to my file.
Same with:

:put=map(range(1,10), 'v:val')

which worked as expected. However using a no-op lambda function:

:put=map(range(1,10), {v -> v})

somehow gets the numbers 0..9 in the file instead of 1..10

This reduced it to the simplest case for demonstration. I stumbled
across it attempting FizzBuzz in a one-liner:

:put=map(range(1, 100), {v -> v % 15 ? v % 5 ? v % 3 ? v : 'Fizz' :
'Buzz' : 'FizzBuzz'})

confused why it kept putting 0/FizzBuzz as the first row.

This is 8.2.1558 on FreeBSD in case it matters:

:ver
VIM - Vi IMproved 8.2 (2019 Dec 12, compiled Oct 4 2020 13:32:14)
Included patches: 1-1558

I'm not sure where I'd start trying to troubleshoot this, but thought
I'd at least mention the oddity here.

-tim




Yegappan Lakshmanan

unread,
Jan 9, 2021, 2:39:39 PM1/9/21
to vim...@googlegroups.com, Vim
Hi, Tim,

On Sat, Jan 9, 2021 at 11:27 AM Tim Chase <v...@tim.thechases.com> wrote:
Tried this:

  :put=range(1,10)

and it worked as expected, appending the numbers 1..10 to my file.
Same with:

  :put=map(range(1,10), 'v:val')

which worked as expected.  However using a no-op lambda function:

  :put=map(range(1,10), {v -> v})

somehow gets the numbers 0..9 in the file instead of 1..10

The lambda function is called with two arguments (the index of the current
item in the list and the value of the item). In your example, you are using
the index of the list item instead of the value. You can try using one of
the following:

     :put=map(range(1, 10), {i, v -> v})
or
     :put=map(range(1, 10), {-> v:val})
 
Regards,
Yegappan

Tim Chase

unread,
Jan 9, 2021, 2:56:58 PM1/9/21
to vim...@googlegroups.com
On 2021-01-09 11:39, Yegappan Lakshmanan wrote:
> The lambda function is called with two arguments (the index of the
> current item in the list and the value of the item).
>
> :put=map(range(1, 10), {i, v -> v})

Ah, that makes sense. I missed that part in the docs:

If {expr2} is a |Funcref| it is called with two arguments:
1. The key or the index of the current item.
2. the value of the current item.

and now I know. Thanks!

-tim



Reply all
Reply to author
Forward
0 new messages