从vim中的每一行抽出第一个单词

时间:2019-06-01 18:47:28

标签: vim

我正在使用vim,我想复制一系列连续行的第一个单词。我唯一想到的是GraphKeys.SUMMARIES(对于第4-32行),但是没有用。谢谢您的任何帮助,谢谢!

2 个答案:

答案 0 :(得分:1)

您可以执行此操作,但是它可能比使用简单的命令要复杂一些。

您尝试运行的是将普通模式命令作为执行命令。那不会像您那样起作用。正常模式下的命令(例如按yw)将无法使用。


要在ex-command模式下运行普通模式命令,应使用normal命令(有关更多信息,请参见:help normal)。 但是,即使您将命令更改为使用普通模式命令(类似:4,32 normal yw),它也仍然无法正常工作,因为它将在每行上运行,并且每次都运行在先前的被选中的值上。

您可以使用vim寄存器执行所需的操作,该寄存器将在每个循环中附加该单词​​(有关寄存器的更多信息,您可以阅读:help registers)。


要执行此操作,应将命令更改为类似:3,32 normal ^"Ayw的内容。

要分解此命令:

  • :-进入命令模式。
  • 3,32-运行命令的范围。
  • normal-要运行的实际命令。
  • ^-转到行的开头。
  • "A-将拉环放入寄存器,将数据附加到先前保存的数据中。
  • yw-输入当前单词。

稍后,要打印复制的值,应在所需位置使用"ap(在正常模式下)。

缺点

请注意,该命令将新字插入寄存器,而忽略寄存器的第一个值。这意味着,如果运行该命令后寄存器不为空,则所有字都将附加到寄存器的当前值之后。

要清除寄存器的先前值,可以运行以下命令:

:let @a=''

在运行yank命令之前。

自动化

如果您想多次执行此操作,则可能需要使用一个简单的函数即可为您完成全部操作,而不是每次都运行两个命令。


执行此操作的简单函数:

function! CopyFirst(first_line, second_line, register)
    execute "let @" . a:register. "=''"
    execute a:first_line . "," . a:second_line . "normal ^\"" . toupper(a:register) . "yw"
endfunction

用法:

:call Copyfirst(3, 32, 'a')
"ap

答案 1 :(得分:0)

此函数使用一个函数范围(:help func-range中有关此功能的更多信息):

" Get the first word of the line for a given range of lines
function! GetFirstWord() range
    let @a=""
    execute a:firstline.",".a:lastline."g/.*/y A"
    echo split(substitute(@a," *\\(\\w\\+\\).\\{-}\\n","\\1 ","g"))
endfunction

第一行清除寄存器 a 。第二行将范围内的行插入寄存器 a 中。最后一行显示带有每个行的第一个单词的列表。输入文件样本:

some sample
   text abc
   123 456
function
yy xx

示例调用和输出:

:2,4call GetFirstWord()
['text', '123', 'function']