가장 오래된 버퍼를 자동으로 닫습니까?


9

최근에 각 파일을 약간 변경하기 위해 많은 파일을 편집해야했습니다. 각 파일에 도달하기 위해 NERDtree를 탐색하고 파일을 하나씩 열었습니다. 점점 더 많은 파일을 열었을 때 메모리 사용량이 많이 증가했음을 알았습니다. vim을 닫으면 많은 기억이 돌아 왔습니다.

플러그인이 많이 설치되어 있지만 메모리 사용량이 크게 증가한 이유는 몇 번의 편집 후에 열린 버퍼 수 때문이라고 생각합니다.

vim이 한 번에 열 수있는 버퍼 수를 제한하여 편집 시간과 관련하여 오래된 버퍼를 자동으로 닫는 방법이 있습니까?

답변:


5

증상을 치료하지 말고 문제를 해결합시다. Vim은 일반적으로 많은 양의 메모리를 사용해서는 안됩니다. 문제를 분리하는 것이 가장 좋습니다. 범인을 찾는 데 도움이되는 몇 가지 팁 :

  • 플러그인 비활성화 (이진 검색을 사용하여 더 빠르게 만들기)
  • ~/.vimrc문제가 있는지 아래로 줄이십시오.
  • ~/.vimrc통해 완전히 비활성화vim -u NONE

vimrc 파일을 어떻게 디버깅합니까?를 참조하십시오 .

플러그인으로 메모리 버그를 발견하면 플러그인 개발자에게 문의하십시오. Vim에서 메모리 버그를 발견하면 오류를 재현하는 단계가 포함 된 버그 보고서를 제출하십시오. 보다:h bugs


+1; Vim에서 gazillion 버퍼를 동시에 열 수 있고 여전히 좋습니다. 버퍼를 보지 않는 한 (윈도우 또는 "탭") 메모리에로드되지 않습니다.
Martin Tournoij

버퍼가 창에 표시되지 않을 때 @Carpetsmoker, 버퍼 변수 및 설정이 사라지지 않습니다. Peter가 제안한 것처럼 플러그인이 각 버퍼에 대해 많은 정보를 저장하면 메모리가 낭비 될 수 있습니다 (최종 사용자는 버퍼로 더 이상 아무것도하지 않을 것입니다). BTW : 플러그인 관리자는 버퍼와 관련된 데이터를 저장할 수 없지만 플러그인 관리자가 공개 "namespace"를 오염시키지 않는 것을 선호 b:variables하는 s:plugin[bufid]경우 에 저장할 수 있습니다 . 이 경우 버퍼를 삭제한다고해서 모든 관련 변수 / 메모리가 반드시 수집되는 것은 아닙니다. b:
Luc Hermitte

5

다음은 귀하의 질문에 답변해야합니다.

function! s:SortTimeStamps(lhs, rhs)
  return a:lhs[1] > a:rhs[1] ? 1 
     \   a:lhs[1] < a:rhs[1] ? -1
     \                       : 0
endfunction

function! s:Close(nb_to_keep)
  let saved_buffers = filter(range(0, bufnr('$')), 'buflisted(v:val) && ! getbufvar(v:val, "&modified")')
  let times = map(copy(saved_buffers), '[(v:val), getftime(bufname(v:val))]')
  call filter(times, 'v:val[1] > 0')
  call sort(times, function('s:SortTimeStamps'))
  let nb_to_keep = min([a:nb_to_keep, len(times)])
  let buffers_to_strip = map(copy(times[0:(nb_to_keep-1)]), 'v:val[0]')
  exe 'bw '.join(buffers_to_strip, ' ') 
endfunction

" Two ways to use it
" - manually
command! -nargs=1 CloseOldBuffers call s:Close(<args>)
" - or automatically
augroup CloseOldBuffers
  au!
  au BufNew * call s:Close(g:nb_buffers_to_keep)
augroup END
" and don't forget to set the option in your .vimrc
let g:nb_buffers_to_keep = 42

이것은 플러그인으로 드롭됩니다. 그런 다음 사용 방법을 선택해야합니다.


3

편집 시간과 관련하여 가장 오래된 버퍼를 얻는 방법을 모르겠지만 대신 가장 오래된 편집되지 않은 버퍼를 닫으려고 시도 할 수 있습니다. 다음과 같은 것 :

function CloseLast ()
    python <<EOF
import vim
N = 10
listed_buffers = [b for b in vim.buffers if b.options['buflisted'] and not b.options['modified']]
for i in range (0, len (listed_buffers) - N):
    vim.command (':bd' + str (listed_buffers[i].number))
EOF
endfunction

autocmd BufNew * call CloseLast()

노트:

  • vim.buffers현재 세션에서 열린 모든 버퍼의 목록이므로 나열되지 않은 버퍼도 포함됩니다. 이 (가) 반환 한 목록과 다릅니다 :ls.
  • 따라서 숨겨 지거나 삭제 된 버퍼를 필터링해야합니다. 을 사용하여 확인할 수 있습니다 options['buflisted'].
  • 마찬가지로 options['modified']버퍼가 수정되었는지 확인합시다.
  • N 열려고하는 수정되지 않은 나열된 버퍼 수입니다.

타임 스탬프를 얻는 방법을 배운 Luc Hermitte의 답변 덕분에 다음을 사용하여 가장 오래된 비활성 항목을 먼저 시작할 수 있습니다.

listed_buffers = (b for b in vim.buffers if b.options['buflisted'] and not b.options['modified'])
oldest_buffers = sorted (listed_buffers, key = lambda b: eval('getftime("' + b.name + '")'))
for i in range (0, len (oldest_buffers) - N):
    vim.command (':bd' + str (oldest_buffers[i].number))

1
파이썬이 필요하지 않습니다. Vim은 충분합니다 : :let buffers = filter(range(0, bufnr('$')), 'buflisted(v:val) && ! getbufvar(v:val, "&modified")')+:exe 'bw '.join(buffers, ' ')
Luc Hermitte

@LucHermitte True이지만 필요없습니다 . Vimscript에 익숙하지 않습니다. IIRC bw의 도움에 따르면 "무엇을하고 있는지 알지 못한다면"사용하지 말아야합니다. 난 아니야 :)
muru

오래된 습관. 나는 항상 사용 :bw하고 결코 사용 하지 않습니다 :bd. 버퍼에서 거의 모든 것을 삭제하는 지점을 보지 못했지만 실제로는 모든 것이 아닙니다.
Luc Hermitte
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.