为什么我的bash函数会完成变量的通配符?

为什么我的bash函数会完成变量的通配符?,bash,function,alias,Bash,Function,Alias,在my~/.bash_别名中: function wtf (){ echo $1; } 在bash中测试: >> wtf t* testes WTF 现在我知道bash在传递通配符之前正在解析我的通配符,我想我应该共享我正在构建的函数。以下是我的递归删除快捷方式的最终版本: # delete recursively function rmr () { find . -name "$1" -type f -delete -exec \ echo $(tput

在my~/.bash_别名中:

function wtf (){
  echo $1;
}
在bash中测试:

>>  wtf t*
testes
WTF


现在我知道bash在传递通配符之前正在解析我的通配符,我想我应该共享我正在构建的函数。以下是我的递归删除快捷方式的最终版本:

# delete recursively
function rmr () {
    find . -name "$1" -type f -delete -exec \
    echo $(tput setaf 1)"deleted >"$(tput setaf 2) {} \; ;
    l;
}

因为您有一个名为
testes
的文件,bash在将参数传递给
wtf()
之前将
t*
替换为。您可能有几个以
t
开头的文件,但是
testes
是第一个,并且
wtf
只回显
$1
。如果用
$*
替换
$1
,您将看到所有这些

例如,如果您有文件
测试
翻滚
(并且没有其他文件以
t开始
),则

wtf t*
bash将用
testes-roll
(空格分隔)替换
t*
,然后评估行

wtf testes tumble
这将导致
wtf
通过
testes
作为
$1
翻滚
作为
$2

如果不希望shell进行文件名扩展,则必须在参数周围加引号,如
wtf't*'
wtf“t*”
。单引号的优点是不仅可以避免文件名扩展,还可以避免任何其他类型的扩展(例如参数扩展和变量扩展)。文件名(或路径名)扩展使用
*
(除其他外),参数和变量扩展使用
$

出于同样的原因,您必须引用
echo
的参数,这次是双引号,因为您希望发生
$1
的参数扩展,但不希望(再次!)发生文件名扩展:

function wtf() {
  echo "$1"
}
manbash
是你的朋友,有很多东西要学


manbash
中,键入
/^EXPANSION
/Pathname EXPANSION
。另请参见
/^QUOTING

这正是shell的工作方式。不是你的函数在做扩展,而是shell在调用你的函数之前做扩展

wtf() {
  echo "$1"
}

wtf 't*'
调用函数和函数内部时,需要引用任何要保留的内容(包括全局字符
*

wtf() {
  echo "$1"
}

wtf 't*'

t*
替换为
“t*”
,以防止bash全局绑定。@Cyrus只延迟全局绑定。展开
$1
(无引号)时,其值也会进行路径名展开。这是不完整的。引用
t*
确实可以防止shell在将模式传递给函数之前扩展模式,但如果将
$1
保留为不带引号,则可以允许shell在参数本身扩展后扩展模式。对我不知道的所有内容的出色描述。现在它有了完美的意义;很明显,我一直在理解bash只是把我的东西推到函数上,然后函数就完成了它需要做的事情。