我正在尝试让我的脚本以“$ variable”形式显示所有文件。*
参数始终是扩展名为.001的文件 我想找到所有具有相同名称但扩展名不同的文件,例如$ file.002,file.003等。例如:
first="$1"
others=${first%.001}
ls $others"*"
我的问题是该文件名为file[success].mpg.001
什么得到了ls,file[success].mpg*
给了我
ls: cannot access file[success].mpg*: No such file or directory
因为ls
需要看到:
file\[success\].mpg*
我一直在尝试一切,我注意到的一件事是 ls喂参数$ 1有效,但是如果在我完成file = $ 1之后输入$ file。 所以我想如何将变量更改为参数?
答案 0 :(得分:7)
您可以使用bash
的{{1}}命令重新格式化字符串。此外,您无需引用printf
:
*
#!/bin/bash
first="$1"
others=$(printf %q "${first%.001}")
ls $others*
以可用作shell输入的格式重新格式化字符串(关于printf %q
的手册页)。
编辑评论:
上述解决方案不适用于文件名中的空格。对于那些情况(如已经提到的其他答案),最好不要使用bash
,而是正确引用所有变量:
printf
答案 1 :(得分:5)
你应该引用变量,而不是通配符:
ls -- "$others"*
双短划线停止搜索选项,以便即使others
以短划线开头,此代码仍然有用。
请注意,ls
通常是脚本中的错误解决方案。仅在您确实要打印列表时使用它,例如长格式:
ls -l -- "$others"*
如果您只想打印名称,则根本不需要ls
:
echo "$others"*
很遗憾,您无法将--
与echo
一起使用。
但是,如果您想要一个文件名数组,请使用
filenames=("$others"*)
如果您想迭代它们,请使用
for filename in "$others"*
答案 2 :(得分:3)
你离我太远了。我的第一个修复是将第3行更改为以下内容:
ls -- "${others}".*
这会扩展$others
并允许全局发生。将*
扩展到所有匹配文件名列表是shell的责任。然后将文件名列表发送到ls
。听起来在大多数情况下,ls会看到类似的东西:
file1.001 file1.002 file1.003 ...
但是,当没有文件存在时,shell将glob传递给ls并且它将看到星号:
file1.*
因此,你的行ls $others"*"
会附加一个字面星号,它将会看到。
除非您有文件名file1.*
(带有文字星号),否则ls
将失败。
另一种选择是使用basename:
first="$1"
others=`basename -- "$first" .001`
ls -- "${others}".*
使用basename
为您提供了删除目录等优势。
但是,正如其他人所指出的那样,根据您对文件列表的处理方式,find
可能会更好。
编辑:双连字符不适用于所有* nix变体,但告诉ls
和basename
命令没有其他cli参数。引用您的变量可能是一种最佳实践,但除了数据不可信外,我更喜欢简单地将它们关闭。了解您的数据和报价。
答案 3 :(得分:1)
使用find代替ls:
$ ls weg.*
ls: weg.*: No such file or directory
$ find . -name weg.\*
$