Bash 脚本错误:“函数:未找到”。为啥会出现这种情况?

Posted

技术标签:

【中文标题】Bash 脚本错误:“函数:未找到”。为啥会出现这种情况?【英文标题】:Bash script error: "function: not found". Why would this appear?Bash 脚本错误:“函数:未找到”。为什么会出现这种情况? 【发布时间】:2012-09-10 05:42:22 【问题描述】:

我正在尝试在我的 Ubuntu 机器上运行 bash script,但它给了我一个错误:

找不到函数

为了进行测试,我创建了以下脚本,该脚本在我的笔记本电脑上运行良好,但在我的台式机上运行良好。关于为什么的任何想法?如果相关的话,我的笔记本电脑是 Mac。

#!/bin/bash

function sayIt    
   echo "hello world"


sayIt

这会在我的笔记本电脑上返回“hello world”,但在我的桌面上会返回:

run.sh: 3: 找不到函数 hello world run.sh: 5: 语法错误: “”意外

【问题讨论】:

想知道您是如何调用脚本的。 【参考方案1】:

很可能在您的桌面上,您实际上并没有在bash 下运行,而是在dash 或其他一些不识别function 关键字的符合POSIX 的shell 下运行。 function 关键字是一个 bashism,一个 bash 扩展。 POSIX 语法不使用 function 并要求使用括号。

$ more a.sh
#!/bin/sh

function sayIt    
   echo "hello world"


sayIt
$ bash a.sh
hello world
$ dash a.sh
a.sh: 3: function: not found
hello world
a.sh: 5: Syntax error: "" unexpected

POSIX 语法适用于以下两种情况:

$ more b.sh
#!/bin/sh

sayIt ()    
   echo "hello world"


sayIt
$ bash b.sh
hello world
$ dash b.sh
hello world

【讨论】:

function 来自 korn shell,它早于 bash。 +1 确实有这个问题,但 bash 仍会按预期执行。至少通过您的解释,我知道为什么如何! :) 那么,如何在 bash 而不是 dash 或 POSIX 兼容的 shell 下运行脚本? 一个可能的原因是脚本没有为执行用户设置执行位,这意味着它被作为普通的 shell 脚本读取。确保这是正确的,并且 shebang 路径实际上调用了 Bash。 对我来说,我正在运行一个 sh 脚本(例如 sh train.sh -d),但它给了我错误。这个答案帮助我意识到了问题(我不得不改写 /bin/bash train.sh -d【参考方案2】:

我遇到了同样的问题,然后我修改了语法,它对我有用。尝试删除关键字function并在函数名后添加方括号() .

#!/bin/bash

sayIt()
   
   echo "hello world"


sayIt

【讨论】:

这不是理想的解决方案,因为两种语法都已定义,但您的语法用于 /bin/sh 脚本,而 function name ... 用于例如/bin/bash。所以 OP 可能使用了错误的解释器(She-Bang 行说它应该是 bash,但是如果您使用 sh ... 显式启动脚本,则该行将被忽略)【参考方案3】:

ls -la /bin/sh

检查指向 bash 或 dash 的符号链接

【讨论】:

为什么#!/bin/bash 不处理这个?【参考方案4】:

对我来说,我刚刚编辑了 bash 配置文件,却忘记了重新启动我的终端会话。

【讨论】:

【参考方案5】:

在函数名后或调用时不需要 () 吗?

function sayIt()  ...


sayIt()

? :)

嗯,实际上,在我的 mac 上,它就像你粘贴的那样工作..

dtpwmbp:~ pwadas$ cat aa.sh 
#!/bin/bash

function sayIt()    
   echo "hello world"


sayIt

dtpwmbp:~ pwadas$ ./aa.sh 
hello world
dtpwmbp:~ pwadas$ 

比较 bash 版本,AFAIR 一些旧版本需要“()”。

dtpwmbp:~ pwadas$ bash --version
GNU bash, version 3.2.48(1)-release (x86_64-apple-darwin12)
Copyright (C) 2007 Free Software Foundation, Inc.
dtpwmbp:~ pwadas$ 

还比较两个 shell 上的 shopt 选项 ( man bash ) 的状态,也许其中一个打开或关闭了一些兼容语法?不带参数的“shopt”命令将列出支持的选项状态。

What is the 'function' keyword used in some bash scripts?

【讨论】:

可悲的是,我真的不知道为什么我对这个问题的回答被否决了:/ 你应该在函数定义中包含(),但在调用函数时不要。 @PiotrWadas,我没有对你投反对票,但这实际上更像是一个问题而不是一个答案。 是的,您的回答确实是关于上述答案的问题。所以它应该是对该答案的评论,而不是答案本身 function foo() 实际上比function foo 无效更多function foo 语法在旧版本的 ksh 和试图保持与它们的兼容性的现代 shell 上受支持,但 需要由符合 1992 POSIX sh 标准的 shell 支持。相比之下,foo() 在所有符合 POSIX 的 shell 上都有效。 function foo() 是这两种格式的混合体,其支持程度不如单独使用任何一种格式。见wiki.bash-hackers.org/scripting/obsolete

以上是关于Bash 脚本错误:“函数:未找到”。为啥会出现这种情况?的主要内容,如果未能解决你的问题,请参考以下文章

为啥安装游戏出现nsis错误?

为啥我的 bash 脚本无法识别 date 命令中的变量?

打开终端并运行 shell 脚本(CentOS)后出现 Bash 错误 [重复]

为啥在 ERR 陷阱中退出 0 时 bash 会抑制标准输出?

检查bash脚本中是不是存在mysql用户,出现错误

如何通过bash脚本检测ant / maven的构建错误?