Ответ 1
Вы можете использовать <C-a>
для выполнения всех совпадений. Поэтому, если вы наберете :bd *.xml
, а затем нажмите <C-a>
, vim завершит команду до :bd file1.xml file2.xml file3.xml
.
Предполагая, что у меня есть несколько файлов, открытых как буферы в Vim. Файлы имеют *.cpp
, *.h
, а некоторые - *.xml
. Я хочу закрыть все файлы XML с помощью :bd *.xml
. Однако Vim этого не допускает (E93: более одного совпадения...).
Есть ли способ сделать это?
P.S. Я знаю, что работает :bd file1 file2 file3
. Могу ли я как-то оценить *.xml
на file1.xml file2.xml file3.xml
?
Вы можете использовать <C-a>
для выполнения всех совпадений. Поэтому, если вы наберете :bd *.xml
, а затем нажмите <C-a>
, vim завершит команду до :bd file1.xml file2.xml file3.xml
.
Вы также можете использовать альтернативно:
:.,$-bd[elete] " to delete buffers from the current one to last but one
:%bd[elete] " to delete all buffers
:3,5bd[elete]
Удалит диапазон буфера от 3 до 5.
Вы можете использовать это.
:exe 'bd '. join(filter(map(copy(range(1, bufnr('$'))), 'bufname(v:val)'), 'v:val =~ "\.xml$"'), ' ')
Это должно быть довольно легко добавить к команде.
function! s:BDExt(ext)
let buffers = filter(range(1, bufnr('$')), 'buflisted(v:val) && bufname(v:val) =~ "\.'.a:ext.'$"')
if empty(buffers) |throw "no *.".a:ext." buffer" | endif
exe 'bd '.join(buffers, ' ')
endfunction
command! -nargs=1 BDExt :call s:BDExt(<f-args>)
Попробуйте script ниже. Пример для "txt", при необходимости измените его, например. на "xml". Измененные буферы не удаляются. Нажмите \bd, чтобы удалить буферы.
map <Leader>bd :bufdo call <SID>DeleteBufferByExtension("txt")
function! <SID>DeleteBufferByExtension(strExt)
if (matchstr(bufname("%"), ".".a:strExt."$") == ".".a:strExt )
if (! &modified)
bd
endif
endif
endfunction
[изменить] То же самое без: bufdo (по просьбе Люка Хермита, см. Комментарий ниже)
map <Leader>bd :call <SID>DeleteBufferByExtension("txt")
function! <SID>DeleteBufferByExtension(strExt)
let s:bufNr = bufnr("$")
while s:bufNr > 0
if buflisted(s:bufNr)
if (matchstr(bufname(s:bufNr), ".".a:strExt."$") == ".".a:strExt )
if getbufvar(s:bufNr, '&modified') == 0
execute "bd ".s:bufNr
endif
endif
endif
let s:bufNr = s:bufNr-1
endwhile
endfunction
У меня тоже была потребность в этой функции все время. Это решение, которое у меня есть в моем vimrc.
function! GetBufferList()
return filter(range(1,bufnr('$')), 'buflisted(v:val)')
endfunction
function! GetMatchingBuffers(pattern)
return filter(GetBufferList(), 'bufname(v:val) =~ a:pattern')
endfunction
function! WipeMatchingBuffers(pattern)
let l:matchList = GetMatchingBuffers(a:pattern)
let l:count = len(l:matchList)
if l:count < 1
echo 'No buffers found matching pattern ' . a:pattern
return
endif
if l:count == 1
let l:suffix = ''
else
let l:suffix = 's'
endif
exec 'bw ' . join(l:matchList, ' ')
echo 'Wiped ' . l:count . ' buffer' . l:suffix . '.'
endfunction
command! -nargs=1 BW call WipeMatchingBuffers('<args>')
Теперь я могу просто сделать :BW regex
(например, :BW \.cpp$
и стереть все соответствующие буферы, которые соответствуют этому шаблону в их имени пути.
Если вы хотите удалить, а не стереть, вы можете, конечно, заменить exec 'bw ' . join(l:matchList, ' ')
на exec 'bd ' . join(l:matchList, ' ')
Очень просто: используйте команду :bd[elete]
. Например, :bd[elete] buf#1 buf#5 buf#3
удалит буферы 1, 3 и 5.
TAB
будет только автозаполнять один файл для вас с Vim 7.4.282
используйте<c-a>
, чтобы автозавершить все файлы.
Вы можете просто использовать:
bd filetype
то просто используйте <c-a>
, чтобы облегчить выполнение всех открытых файлов указанного типа файлов.
например, у вас есть 1.xml, 2.xml, 3.xml и 4.xml, вы можете сделать:
bd xml
затем нажмите <c-a>
vim будет автозаполнен для вас следующим образом:
bd 1.xml 2.xml 3.xml 4.xml
вы можете просто нажать Enter, чтобы выполнить команду.
если вы внесли изменения в один из файлов, упомянутых выше, не забудьте сделать:
bd! xml