我确信你们中的许多人都熟悉pathmunge
Bourne shell 兼容的点文件中使用的规范函数,以防止变量中出现重复条目PATH
。我还为LD_LIBRARY_PATH
和变量创建了类似的函数MANPATH
,因此我的 中有以下三个函数.bashrc
:
# function to avoid adding duplicate entries to the PATH
pathmunge () {
case ":${PATH}:" in
*:"$1":*)
;;
*)
if [ "$2" = "after" ] ; then
PATH=$PATH:$1
else
PATH=$1:$PATH
fi
esac
}
# function to avoid adding duplicate entries to the LD_LIBRARY_PATH
ldpathmunge () {
case ":${LD_LIBRARY_PATH}:" in
*:"$1":*)
;;
*)
if [ "$2" = "after" ] ; then
LD_LIBRARY_PATH=$LD_LIBRARY_PATH:$1
else
LD_LIBRARY_PATH=$1:$LD_LIBRARY_PATH
fi
esac
}
# function to avoid adding duplicate entries to the MANPATH
manpathmunge () {
case ":${MANPATH}:" in
*:"$1":*)
;;
*)
if [ "$2" = "after" ] ; then
MANPATH=$MANPATH:$1
else
MANPATH=$1:$MANPATH
fi
esac
}
有没有什么优雅的方法可以将这三个功能合二为一,以保持文件.bashrc
更小?也许我可以通过一种方式传递要检查/设置的变量,类似于 C 中的引用传递?
答案1
您可以使用eval
已知变量名称来获取和设置变量的值;以下函数在 Bash 和短跑:
varmunge ()
{
: '
Invocation: varmunge <varname> <dirpath> [after]
Function: Adds <dirpath> to the list of directories in <varname>. If <dirpath> is
already present in <varname> then <varname> is left unchanged. If the third
argument is "after" then <dirpath> is added to the end of <varname>, otherwise
it is added at the beginning.
Returns: 0 if everthing was all right, 1 if something went wrong.
' :
local pathlist
eval "pathlist=\"\$$1\"" 2>/dev/null || return 1
case ":$pathlist:" in
*:"$2":*)
;;
"::")
eval "$1=\"$2\"" 2>/dev/null || return 1
;;
*)
if [ "$3" = "after" ]; then
eval "$1=\"$pathlist:$2\"" 2>/dev/null || return 1
else
eval "$1=\"$2:$pathlist\"" 2>/dev/null || return 1
fi
;;
esac
return 0
}
答案2
在 Bash 4.3 或更高版本中,您可以使用 来declare -n
通过引用有效地传递变量。
# function to avoid adding duplicate entries to the PATH
pathmunge () {
declare -n thepath=$1
case ":${thepath}:" in
*:"$2":*)
;;
*)
if [ "$3" = "after" ] ; then
thepath=$thepath:$2
else
thepath=$2:$thepath
fi
;;
esac
}
你可以这样称呼它:
pathmunge PATH ~/bin
pathmunge MANPATH /usr/local/man after