How to get a list of files that match some pattern if filenames may contain \n
character?
Update: I want solution in pure vimscript, so that it will depend on nothing but vim.
Update2:
Expected output of glob function
Consider the following script:
开发者_开发知识库:!touch /test ; mkdir /test$'\n' ; touch /test$'\n'/test
:echo glob('/**/test')
/test
/test
/test
That is the output of glob
function. I want it be the following:
:echo NewGlob('/**/test')
['/test', '/test
/test']
you may try using ls
with -b
option. check the man page
:echo split( glob("pattern", '.'), "\r")
If you want the pattern to match files containing \n
exclusively, use "*\n*"
.
EDIT:
I see, the character you use in the filename is the same as the one used by glob()
to distinguish results. As a consequence, we can't rely of glob()
.
ghostdog74 gave a good answer then:
:echo split( system('ls -1bd test*'), "\n")
Of course, this is not portable. But I do not really call this the general case -- I never see this kind of names. If glob()
cannot handle this general case, then glob()
must be fixed.
May be you can try with embedded python or ruby as arnold suggested. But that isn't portable either.
Try this python program. It will match files like abc\n1
, abc\n2abc
etc.
#!/usr/bin/env python
import os, re
dirlist = os.listdir('.')
pattern = 'abc\n\\d'
for fname in dirlist:
if re.search(pattern, fname):
print fname.replace('\n', '\\n')
It will replace line end ('\n
') characters with "\n
" string for clarity.
I finally had to write the following function that returns just the same results as python's os.listdir:
function s:globdir(directory, ...)
return split(glob(escape(a:directory.g:os#pathSeparator, '`*[]\').
\ get(a:000, 0, '*')),
\"\n", 1)
endfunction
function s:GetDirContents(directory)
let dirlist = s:globdir(a:directory)+s:globdir(a:directory, '.*')
let nlnum=len(split(a:directory, "\n", 1))-1
let r=[]
let i=0
let addfragment=""
for directory in dirlist
if i<nlnum
let i+=1
let addfragment=directory."\n"
continue
else
let directory=addfragment.directory
let i=0
let addfragment=""
endif
let tail=fnamemodify(directory, ':t')
if tail==#'.' || tail==#'..'
continue
endif
if directory[0]!=#'/'
let r[-1].="\n".directory
else
call add(r, tail)
endif
endfor
return r
endfunction
精彩评论