对于目录中的文件,仅回显文件名(无路径)


98

如果使用for循环遍历目录,如何只回显文件的文件名?

for filename in /home/user/*
do
  echo $filename
done;

将使用文件名提取完整路径。我只想要文件名。

Answers:


166

如果您想要本机bash解决方案

for file in /home/user/*; do
  echo "${file##*/}"
done

上面使用了Shell固有的Parameter Expansion,不需要调用外部二进制文件,例如basename

但是,我可能建议仅使用 find

find /home/user -type f -printf "%f\n"

9
好答案。对于那些有兴趣了解更多有关参数扩展的人员:wiki.bash-hackers.org/syntax/pe#substring_removal
DougW 2012年

1
-printf:未知的主节点
Nobita,

2
考虑更改${file##*/}"${file##*/}"支持带空格的文件名,例如“带空格.txt的我的文件名”。
WinEunuuchs2Unix

echo“ $ {file ## * /}”返回一个空字符串
Alessandro C

47

只需使用basename

echo `basename "$filename"`

如果$ filename包含空格,则需要使用引号。


3
更好地使用参数扩展,不需要调用外部二进制文件。
SiegeX

5
顺便说一句,``已弃用。最好使用$()像奥利那样
SiegeX

1
很抱歉在这个旧答案上发表评论,但是basename对于有空间的文件无法正常工作。示例:pwd输出:/test 1basename $(pwd)输出:test。在OS X和Ubuntu Server(14.04)上进行了测试。@SiegeX建议使用本机bash解决方案对我有用。
MarkoGrešak,2014年

@MarkoGrešak使用basename "$(pwd)"代替。
YoungFrog

@YoungFrog感谢您的输入,但这是9个月前。同样,最好使用变量$PWD而不是运行命令。
MarkoGrešak2015年

15

用途basename

echo $(basename /foo/bar/stuff)

你为什么用echobasename已经打印了结果。echo如果不引用subshel​​l,甚至可能会破坏结果。示例:echo $(basename path/with\ \ spaces)打印不正确with spaces(仅一个空格)。
Socowi '19

7

另一种方法是ls在读取目录中的文件列表时使用,以便为您提供所需的内容,即“仅文件名”。与读取完整文件路径然后在for循环的主体中提取“文件名”组件相反。

以下是原始示例的示例:

for filename in $(ls /home/user/)
do
  echo $filename
done;

如果您在与文件相同的目录中运行脚本,那么它将变成:

for filename in $(ls)
do
  echo $filename
done;

1
ls包括*通常不进行扩展的任何点文件。此外for f in $(...) ...,如果任何文件名包含空格,除非你设置IFS,可如果有文件名包含水珠字符,除非你设置-f / -o noglob,并根据系统或壳失败失败echo,如果任何文件名是连字符+字母或包含反斜杠可能会失败。OTOH ls -1 /path/to/dir本身就可靠地将每个文件名打印在一行上,以点文件的差异为模。
dave_thompson_085 '19

0

如果只需要文件名:

for file in /home/user/*; do       
  f=$(echo "${file##*/}");
  filename=$(echo $f| cut  -d'.' -f 1); #file has extension, it return only filename
  echo $filename
done

有关cut命令的更多信息,请参见此处

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.