【问题标题】:meta programming in bash/zsh to reload shell scriptbash/zsh 中的元编程以重新加载 shell 脚本
【发布时间】:2019-09-21 16:14:30
【问题描述】:

我有三个 zsh 脚本,

meta_zsh.sh,

# meta_zsh.sh
meta_s() {
    eval 'echo "${(%):-%x} re-define s()"; s() { echo " calling s() ${(%):-%x}"; }'
}

script_zsh.shscript_zsh_2.sh(内容相同)

# script_zsh.sh and script_zsh_2.sh (the same content)
meta_s
s

在zsh中执行以下命令

$ . ./meta_zsh.sh; . ./script_zsh.sh; . ./script_zsh_2.sh

输出

./meta_zsh.sh re-define s()
  calling s() ./script_zsh.sh
./meta_zsh.sh re-define s()
  calling s() ./script_zsh_2.sh

问题是,如何在bash中达到同样的效果?

我尝试将${(%):-%x} 更改为${BASH_SOURCE[0]}$0,但都不起作用。

何必呢?

以上 meta_xx.sh 来源于~/.zshrc (~/.bashrc) 之后,

我可以在 shell 中输入s 来重新加载最近的源脚本, 如果meta_s 在里面。

【问题讨论】:

  • 也许你在搜索$FUNCNAME...${FUNCNAME}!?
  • 是不是用来取回函数名的,如果是,那就不是。我的需要是动态扩展为脚本的名称,而不是函数的名称。

标签: bash metaprogramming zsh


【解决方案1】:

BASH_SOURCE实际上是调用者堆栈,${BASH_SOURCE[0]}是当前文件,所以你可以使用${BASH_SOURCE[1]}

$ cat meta.sh 
meta_s() {
    eval 'CALLER=${BASH_SOURCE[1]}; echo "$CALLER re-define s()"; s() { echo " calling s() $CALLER"; }'
}
$ cat s1.sh 
meta_s
s
$ cat s2.sh 
meta_s
s
$ . meta.sh ; . s1.sh ; . s2.sh 
s1.sh re-define s()
 calling s() s1.sh
s2.sh re-define s()
 calling s() s2.sh

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-03-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-10-24
    • 2021-11-15
    • 1970-01-01
    相关资源
    最近更新 更多