I asked this question, about how to find where one word is close to another word, and Quasimodo gave the very fine answer:


Now I want to parametrize this command into something easy-to-remember, such as:

:PS first 10 derivative

which would find instances of the word "first" occurring within 10 words of the word "derivative". User B Layer came up with the code

com! -nargs=+ PS let @/ = printf('\v%s(\W+\w+){,%d}\W+%s', <f-args>)

I have a gut feeling that this is very close to what's needed, but this doesn't work. When I try to execute this, nothing happens, even when I know from executing


that there should be hits. I also tried defining

com! -nargs=+ PS let @/ = printf('/\v%s(\W+\w+){,%d}\W+%s', <f-args>)

but no joy. Any ideas what's wrong with this command definition?

One thought: it looks like we're defining a macro; can you use arguments with macros like that?

Another thought: am I invoking the command incorrectly? Should I just define the macro and invoke it in a macro-like way?

I don't know what I don't know, so any help is appreciated.

[EDIT] I just found out that B Layer's command allows me to define the macro as I go. Then, to do the actual searching, I invoke the macro in the normal way: @a, if I've done

com! -nargs=+ PS let @a = printf('/\v%s(\W+\w+){,%d}\W+%s', <f-args>)

This works, but I'd prefer a one-step process, if possible. Just invoking :PS first 10 derivative actually does the search, instead of defining a macro that I invoke in a separate step.

Many thanks!

  • 1
    You assign slash-register, but you never use it.
    – Matt
    Sep 12, 2020 at 19:52
  • @Matt: Yep, just figured that out! See the edit. Sep 12, 2020 at 19:52

1 Answer 1

com! -nargs=+ PS let @/ = printf('\v%s(\W+\w+){,%d}\W+%s', <f-args>)

The way this is intended to work is to act as if you entered, after hitting /, the same search term that was provided in the answer to your question. So when you run the command you just need to use n and N to go forward and back to any matches.

The / register always contains the last pattern that was entered after the / Normal mode command was typed. You can directly set this, though. IOW, when you set it with let @/ = foo it's just like you entered /foo.

My command is a convenient way to run a search that contains some fixed regex bits and some parts that vary. You just enter the parts that vary and it will fill in the parts that are fixed and dump both into @/...the end result being that it's kinda like you had hand typed the whole thing after hitting / in Normal mode. If you use DBK's suggestion in the comments of adding | normal! n at the end of the command then it should be just like it.

Note that I said in my comment that it's not possible to do something starting with /, which is what you requested. I kinda lied. ;) It's technically possible since you can remap / to anything but that's getting into tricky territory (certainly more than I wanted to cover in a comment). I've entered that territory before and you need to write some solid code to have a problem free experience. You're basically creating a wrapper around the native / command and need to capture only those things specific to your problem space while accurately letting everything else through to the native command. Possible? Yes. Worth it? Depends on how much you want it. I have an answer that describes the general requirements here: Can I use a different color for the selected match than for other matches

  • 3
    I guess you could always add | normal! n at the end, no?
    – D. Ben Knoble
    Sep 12, 2020 at 21:09
  • Yeah, you could do that. I have hlsearch enabled so things light up after running the command if there's something in view. Both provide some feedback that the command is doing something.
    – B Layer
    Sep 12, 2020 at 21:11
  • Yep, this does work as you say. That's good enough for me, thanks much! Sep 12, 2020 at 21:16
  • Great. You're welcome.
    – B Layer
    Sep 12, 2020 at 21:17
  • 1
    Oh, man: this is great! I'm trying to compile an index for my father's calculus book, and this trick here is saving me so much time! Hard to thank you enough for it. Sep 12, 2020 at 21:23

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.