Bash 如何筛选函数/别名以仅查找用户定义的函数/别名?
我试图查看有关函数和别名的信息,并使用此函数向我显示它们的定义。但是,它不仅显示了我的概要文件脚本定义的函数/别名,还显示了许多其他内容(我不太感兴趣)Bash 如何筛选函数/别名以仅查找用户定义的函数/别名?,bash,function,alias,Bash,Function,Alias,我试图查看有关函数和别名的信息,并使用此函数向我显示它们的定义。但是,它不仅显示了我的概要文件脚本定义的函数/别名,还显示了许多其他内容(我不太感兴趣) 是否有办法只显示在.bashrc.profile等中专门设置的函数/别名(即用户定义的函数/别名) 是否可以查看此shell中定义的函数或别名的日期/时间,是否可以查看源代码,如.bashrc或.profile等(可能不会保留此类信息,但所有命令历史日期/时间戳都会保留,因此我想可能是这样的) def() { 如果[-z“$1”];则 声明
- 是否有办法只显示在
.bashrc
等中专门设置的函数/别名(即用户定义的函数/别名).profile
- 是否可以查看此shell中定义的函数或别名的日期/时间,是否可以查看源代码,如
或.bashrc
等(可能不会保留此类信息,但所有命令历史日期/时间戳都会保留,因此我想可能是这样的).profile
def()
{
如果[-z“$1”];则
声明-F;
printf“\n上面列出的是所有定义的函数'declare-F'(使用def显示函数内容)\n键入'alias'显示所有别名(def显示别名定义,其中'def'使用'command-V')\n\n”;
其他的
命令-V$1;
fi
}
一种方法,将已知函数列表缓存在点文件的顶部(因此未缓存的任何函数都可以被视为未知):
declare-A-g预定义_命令
填充预定义的命令(){
本地线路fndec\u re别名\u re
fndec_re='^declare-f([^[:space:]+)$'
别名_re='^alias([^[:space:=])+='
当IFS=读取-r行时;执行
[[$line=~$fndec\u re]&&预定义的\u命令[${BASH\u REMATCH[1]}]=1
done<就我个人的做法而言,我会启动您的点文件初始化一个关联数组,列出已定义的项,并从显示函数中过滤掉它们(使用关联数组特别意味着您得到O(1)查找性能,但如果您的目标是MacOS,其古老的bash 3.2不再是一个选项)…然而,这是一个非常广泛的问题,因为它所陈述的目标可以通过多种方式实现。(bash不跟踪函数定义的时间,但它跟踪定义它的代码来自何处——这对于在运行时正确设置bash_SOURCE
和类似值是必要的)…也就是说,请注意,只跟踪函数的源文件,而不跟踪别名(因为别名实际上根本不是一种语言特性;它们只是在解析器进行任何实际分析之前发生的前缀替换;因为它们在解析时间之后“不存在”,所以它们不存在于堆栈跟踪中,所以不需要跟踪它们的源文件)顺便说一下,考虑<代码> Prtff '%s\n '第一行'''第二行'',当你想打印多行时,上一行是空白的。如果<代码> \n′/COD>是你使用过的唯一的转义序列,没有理由重复它。我很想看看你是怎么做到的,查尔斯,听起来真的很有趣,很有用(!).我远离MacOS,它们在我看来“不是电脑”
def ()
{
if [ -z "$1" ]; then
declare -F;
printf "\nAbove listing is all defined functions 'declare -F' (use def <func-name> to show function contents)\nType 'alias' to show all aliases (def <alias-nam> to show alias definition, where 'def' uses 'command -V <name>')\n\n";
else
command -V $1;
fi
}
declare -A -g predefined_commands
populate_predefined_commands() {
local line fndec_re alias_re
fndec_re='^declare -f ([^[:space:]]+)$'
alias_re='^alias ([^[:space:]=])+='
while IFS= read -r line; do
[[ $line =~ $fndec_re ]] && predefined_commands[${BASH_REMATCH[1]}]=1
done < <(declare -F)
while IFS= read -r line; do
[[ $line =~ $alias_re ]] && predefined_commands[${BASH_REMATCH[1]}]=1
done < <(alias -p)
}
def() {
if [[ $1 ]]; then
command -V -- "$1"
return
fi
local line fndec_re alias_re
fndec_re='^declare -f ([^[:space:]]+)$'
alias_re='^alias ([^[:space:]=])+='
while IFS= read -r line; do
[[ $line =~ $fndec_re ]] && [[ ${predefined_commands[${BASH_REMATCH[1]}]} ]] && continue
printf '%s\n' "$line"
done < <(declare -F)
while IFS= read -r line; do
[[ $line =~ $alias_re ]] && [[ ${predefined_commands[${BASH_REMATCH[1]}]} ]] && continue
printf '%s\n' "$line"
done < <(alias -p)
}
# do this AFTER calling def, or else def itself will show up as a new function
populate_predefined_commands; unset -f populate_predefined_commands