Vim은 ctag를 자동 생성합니다.
지금은 다음과 같습니다 .vimrc
.
au BufWritePost *.c,*.cpp,*.h !ctags -R
여기에는 몇 가지 문제가 있습니다.
- 느립니다-마지막 태그 생성 이후 변경되지 않은 파일에 대한 태그를 다시 생성합니다.
- 필연적으로 "계속하려면 Enter를 누르거나 명령을 입력하십시오"라는 이유로 파일을 작성한 후 다시 Enter 버튼을 눌러야 합니다 .
이 두 가지 문제를 결합하면 너무 빨리 ( ctags -R
완료 되기 전에) 추가 입력을 밀고 성가신 오류 메시지가 표시되고 다시 입력해야합니다.
나는 그것이 큰 문제처럼 들리지 않는다는 것을 알고 있지만, 내가 주어진 날에하는 파일 쓰기의 양으로 인해 정말 짜증나는 경향이 있습니다. 더 나은 방법이 있어야합니다!
au BufWritePost *.c,*.cpp,*.h silent! !ctags -R &
단점은 완료 될 때까지 유용한 태그 파일이 없다는 것입니다. * nix 시스템을 사용하는 한 이전 ctag가 완료되기 전에 여러 번 쓰기를해도 괜찮지 만 테스트해야합니다. Windows 시스템에서는 백그라운드에 배치하지 않고 첫 번째 ctag가 완료 될 때까지 파일이 잠겨 있다고 불평합니다 (vim에서 문제를 일으키지는 않지만 약간 오래된 태그 파일로 끝납니다) ).
--append
tonylo가 제안한대로 옵션을 사용할 수 있지만 비활성화 tagbsearch
해야 태그 파일의 크기에 따라 태그 검색이 훨씬 오래 걸릴 수 있습니다.
편집 : 다음과 같은 솔루션 이 AutoTag vim 스크립트 로 게시되었습니다 . 그러나 스크립트 에는 Python을 지원하는 vim이 필요합니다 .
내 솔루션은 대신 awk를 사용하므로 더 많은 시스템에서 작동합니다.
au FileType {c,cpp} au BufWritePost <buffer> silent ! [ -e tags ] &&
\ ( awk -F'\t' '$2\!="%:gs/'/'\''/"{print}' tags ; ctags -f- '%:gs/'/'\''/' )
\ | sort -t$'\t' -k1,1 -o tags.new && mv tags.new tags
스크립트에서 이런 식으로 만 작성할 수 있습니다. 그렇지 않으면 한 줄로 작성해야합니다.
거기에 많은 일이 있습니다.
이 자동 명령은 파일이 C 또는 C ++로 감지 될 때 트리거되고
BufWritePost
이벤트 에 의해 트리거되는 버퍼 로컬 자동 명령을 차례로 추가합니다 .그것은 사용
%
투게더와, 실행 시간에 상기 버퍼의 파일명으로 대체 자리:gs
개질제 (인용 탈출 인용 인용에 임베디드 작은 따옴표 돌려) 파일명 쉘 인용 사용.그런 식으로
tags
파일이 존재 하는지 확인하는 셸 명령을 실행합니다 .이 경우 방금 저장된 파일을 참조하는 행을 제외하고 내용이 인쇄되고 방금 저장된 파일ctags
에서만 호출되며 결과는 다음과 같습니다.sort
에드 및 제자리에 다시 넣습니다.
경고 구현 자 : 이것은 모든 것이 동일한 디렉토리에 있고 버퍼 로컬 현재 디렉토리라고 가정합니다. 나는 경로 맹 글링에 대해 전혀 생각하지 않았습니다.
이 작업을 수행하기 위해 easytags.vim 을 작성 했습니다. 자동으로 태그를 업데이트하고 강조 표시합니다. 플러그인은 편집중인 파일 만 업데이트하거나 편집중인 파일의 디렉토리에있는 모든 파일을 (재귀 적으로) 업데이트하도록 구성 할 수 있습니다. 글로벌 태그 파일, 파일 유형별 태그 파일 및 프로젝트 별 태그 파일을 사용할 수 있습니다.
나는 이것이 오래된 쓰레드라는 것을 알아 챘지만 ... inotify를 지원하는 환경과 같은 * nix에서 incron 을 사용하라 . 디렉토리의 파일이 변경 될 때마다 항상 명령을 실행합니다. 즉,
/home/me/Code/c/that_program IN_DELETE,IN_CLOSE_WRITE ctags --sort=yes *.c
그게 다야.
다음과 같이 ctags에 append 인수를 사용할 수 있습니다.
http://vim.wikia.com/wiki/Autocmd_to_update_ctags_file
나는 일반적으로 코드 브라우징에 소스 통찰력을 사용하기 때문에 이것을 보증 할 수는 없지만 vim을 편집기로 사용합니다.
crontab을 통해 실행되도록 ctag를 예약하는 것은 어떻습니까? 프로젝트 트리가 구조상 상당히 안정적이라면 가능해야합니까?
"press enter"프롬프트를 표시하지 않으려면 : silent를 사용 하십시오 .
OSX에서이 명령은 적어도 나를 위해 작동하지 않습니다.
au BufWritePost *.c,*.cpp,*.h silent! !ctags -R &
-R 옵션이 포함 된 표준 ctags 버전을 얻는 방법을 설명하는 게시물을 찾았 습니다 . 이것만으로는 효과가 없었습니다. Homebrew가 프로그램을 설치하는 bin을 선택하기 위해 .bash_profile의 PATH 변수에 / usr / local / bin을 추가해야했습니다.
내 의견에서 플러그인 Indexer가 더 좋습니다.
http://www.vim.org/scripts/script.php?script_id=3221
그것은 될 수 있습니다:
1) project.tar.gz에 대한 추가 기능
2) 독립 플러그인
- 백그라운드 태그 생성 (ctags가 작동하는 동안 기다리지 않음)
- 여러 프로젝트 지원
정말 잘 작동하는 AutoTag 라는 vim 플러그인 이 있습니다.
taglist가 설치되어있는 경우에도 업데이트됩니다.
--append
옵션은 실제로 길을 가야하는 것입니다. 와 함께 사용하면 태그가 지정된 파일을 grep -v
하나만 업데이트 할 수 있습니다 . 예를 들어, 다음은 이 문제를 해결 하는 닦지 않은 플러그인 의 일부입니다 . (주의 : "외부" 라이브러리 플러그인 이 필요합니다. )
" Options {{{1
let g:tags_options_cpp = '--c++-kinds=+p --fields=+imaS --extra=+q'
function! s:CtagsExecutable()
let tags_executable = lh#option#Get('tags_executable', s:tags_executable, 'bg')
return tags_executable
endfunction
function! s:CtagsOptions()
let ctags_options = lh#option#Get('tags_options_'.&ft, '')
let ctags_options .= ' '.lh#option#Get('tags_options', '', 'wbg')
return ctags_options
endfunction
function! s:CtagsDirname()
let ctags_dirname = lh#option#Get('tags_dirname', '', 'b').'/'
return ctags_dirname
endfunction
function! s:CtagsFilename()
let ctags_filename = lh#option#Get('tags_filename', 'tags', 'bg')
return ctags_filename
endfunction
function! s:CtagsCmdLine(ctags_pathname)
let cmd_line = s:CtagsExecutable().' '.s:CtagsOptions().' -f '.a:ctags_pathname
return cmd_line
endfunction
" ######################################################################
" Tag generating functions {{{1
" ======================================================================
" Interface {{{2
" ======================================================================
" Mappings {{{3
" inoremap <expr> ; <sid>Run('UpdateTags_for_ModifiedFile',';')
nnoremap <silent> <Plug>CTagsUpdateCurrent :call <sid>UpdateCurrent()<cr>
if !hasmapto('<Plug>CTagsUpdateCurrent', 'n')
nmap <silent> <c-x>tc <Plug>CTagsUpdateCurrent
endif
nnoremap <silent> <Plug>CTagsUpdateAll :call <sid>UpdateAll()<cr>
if !hasmapto('<Plug>CTagsUpdateAll', 'n')
nmap <silent> <c-x>ta <Plug>CTagsUpdateAll
endif
" ======================================================================
" Auto command for automatically tagging a file when saved {{{3
augroup LH_TAGS
au!
autocmd BufWritePost,FileWritePost * if ! lh#option#Get('LHT_no_auto', 0) | call s:Run('UpdateTags_for_SavedFile') | endif
aug END
" ======================================================================
" Internal functions {{{2
" ======================================================================
" generate tags on-the-fly {{{3
function! UpdateTags_for_ModifiedFile(ctags_pathname)
let source_name = expand('%')
let temp_name = tempname()
let temp_tags = tempname()
" 1- purge old references to the source name
if filereadable(a:ctags_pathname)
" it exists => must be changed
call system('grep -v " '.source_name.' " '.a:ctags_pathname.' > '.temp_tags.
\ ' && mv -f '.temp_tags.' '.a:ctags_pathname)
endif
" 2- save the unsaved contents of the current file
call writefile(getline(1, '$'), temp_name, 'b')
" 3- call ctags, and replace references to the temporary source file to the
" real source file
let cmd_line = s:CtagsCmdLine(a:ctags_pathname).' '.source_name.' --append'
let cmd_line .= ' && sed "s#\t'.temp_name.'\t#\t'.source_name.'\t#" > '.temp_tags
let cmd_line .= ' && mv -f '.temp_tags.' '.a:ctags_pathname
call system(cmd_line)
call delete(temp_name)
return ';'
endfunction
" ======================================================================
" generate tags for all files {{{3
function! s:UpdateTags_for_All(ctags_pathname)
call delete(a:ctags_pathname)
let cmd_line = 'cd '.s:CtagsDirname()
" todo => use project directory
"
let cmd_line .= ' && '.s:CtagsCmdLine(a:ctags_pathname).' -R'
echo cmd_line
call system(cmd_line)
endfunction
" ======================================================================
" generate tags for the current saved file {{{3
function! s:UpdateTags_for_SavedFile(ctags_pathname)
let source_name = expand('%')
let temp_tags = tempname()
if filereadable(a:ctags_pathname)
" it exists => must be changed
call system('grep -v " '.source_name.' " '.a:ctags_pathname.' > '.temp_tags.' && mv -f '.temp_tags.' '.a:ctags_pathname)
endif
let cmd_line = 'cd '.s:CtagsDirname()
let cmd_line .= ' && ' . s:CtagsCmdLine(a:ctags_pathname).' --append '.source_name
" echo cmd_line
call system(cmd_line)
endfunction
" ======================================================================
" (public) Run a tag generating function {{{3
function! LHTagsRun(tag_function)
call s:Run(a:tag_function)
endfunction
" ======================================================================
" (private) Run a tag generating function {{{3
" See this function as a /template method/.
function! s:Run(tag_function)
try
let ctags_dirname = s:CtagsDirname()
if strlen(ctags_dirname)==1
throw "tags-error: empty dirname"
endif
let ctags_filename = s:CtagsFilename()
let ctags_pathname = ctags_dirname.ctags_filename
if !filewritable(ctags_dirname) && !filewritable(ctags_pathname)
throw "tags-error: ".ctags_pathname." cannot be modified"
endif
let Fn = function("s:".a:tag_function)
call Fn(ctags_pathname)
catch /tags-error:/
" call lh#common#ErrorMsg(v:exception)
return 0
finally
endtry
echo ctags_pathname . ' updated.'
return 1
endfunction
function! s:Irun(tag_function, res)
call s:Run(a:tag_function)
return a:res
endfunction
" ======================================================================
" Main function for updating all tags {{{3
function! s:UpdateAll()
let done = s:Run('UpdateTags_for_All')
endfunction
" Main function for updating the tags from one file {{{3
" @note the file may be saved or "modified".
function! s:UpdateCurrent()
if &modified
let done = s:Run('UpdateTags_for_ModifiedFile')
else
let done = s:Run('UpdateTags_for_SavedFile')
endif
endfunction
이 코드는 다음을 정의합니다.
^Xta
현재 프로젝트의 모든 파일에 대한 태그 기반 업데이트를 강제합니다.^Xtc
현재 (저장되지 않은) 파일에 대한 태그 기반 업데이트를 강제합니다.- an autocommand that updates the tags base every time a file is saved ; and it supports and many options to disable the automatic update where we don't want it, to tune ctags calls depending on filetypes, ... It is not just a tip, but a small excerpt of a plugin.
HTH,
Auto Tag is a vim plugin that updates existing tag files on save.
I've been using it for years without problems, with the exception that it enforces a maximum size on the tags files. Unless you have a really large set of code all indexed in the same tags file, you shouldn't hit that limit, though.
Note that Auto Tag requires Python support in vim.
ReferenceURL : https://stackoverflow.com/questions/155449/vim-auto-generate-ctags
'programing' 카테고리의 다른 글
필수 하위 구문 분석기가있는 Argparse (0) | 2021.01.14 |
---|---|
gulp는 모든 CSS 파일을 단일 파일로 축소합니다. (0) | 2021.01.14 |
C # Decimal 데이터 형식 성능 (0) | 2021.01.14 |
“_vti_cnf”,“_vti_pvt”,“_vti_script”및“_vti_txt”폴더는 무엇입니까? (0) | 2021.01.14 |
메타 태그가 문서 본문에 있으면 어떻게됩니까? (0) | 2021.01.14 |