基本上我需要运行与shell脚本文件位置相关的路径脚本,我如何将当前目录更改为脚本文件所在的相同目录?
当前回答
假设您正在使用bash
#!/bin/bash
current_dir=$(pwd)
script_dir=$(dirname "$0")
echo $current_dir
echo $script_dir
这个脚本应该打印您所在的目录,然后是脚本所在的目录。例如,当使用/home/mez/中的脚本从/调用它时,它输出
/
/home/mez
请记住,当从命令的输出为变量赋值时,请将命令包装在$(and)中—否则将得不到所需的输出。
其他回答
这个问题的最佳答案是: 从内部获取Bash脚本的源目录
它是:
DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
一行代码,它将提供脚本的完整目录名,无论从哪里调用脚本。
要了解它是如何工作的,你可以执行以下脚本:
#!/bin/bash
SOURCE="${BASH_SOURCE[0]}"
while [ -h "$SOURCE" ]; do # resolve $SOURCE until the file is no longer a symlink
TARGET="$(readlink "$SOURCE")"
if [[ $TARGET == /* ]]; then
echo "SOURCE '$SOURCE' is an absolute symlink to '$TARGET'"
SOURCE="$TARGET"
else
DIR="$( dirname "$SOURCE" )"
echo "SOURCE '$SOURCE' is a relative symlink to '$TARGET' (relative to '$DIR')"
SOURCE="$DIR/$TARGET" # if $SOURCE was a relative symlink, we need to resolve it relative to the path where the symlink file was located
fi
done
echo "SOURCE is '$SOURCE'"
RDIR="$( dirname "$SOURCE" )"
DIR="$( cd -P "$( dirname "$SOURCE" )" && pwd )"
if [ "$DIR" != "$RDIR" ]; then
echo "DIR '$RDIR' resolves to '$DIR'"
fi
echo "DIR is '$DIR'"
这一行代码告诉shell脚本在哪里,与您是否运行它或是否获取它无关。此外,它还会解析所涉及的任何符号链接,如果是这样的话:
dir=$(dirname $(test -L "$BASH_SOURCE" && readlink -f "$BASH_SOURCE" || echo "$BASH_SOURCE"))
顺便说一下,我认为您正在使用/bin/bash.
对于tcsh,您可以使用:h变量修饰符来检索路径。
需要注意的是,如果脚本作为tcsh myscript执行。Csh,那么您将只获得脚本名称。一个解决方法是验证路径,如下所示。
#!/bin/tcsh
set SCRIPT_PATH = $0:h
if ( $SCRIPT_PATH == $0 ) then
set SCRIPT_PATH = "."
endif
$SCRIPT_PATH/compile.csh > $SCRIPT_PATH/results.txt
关于变量修饰语的更多信息可以在https://learnxinyminutes.com/docs/tcsh/上找到
So many answers, all plausible, each with pro's and con's & slightly differeing objectives (which should probably be stated for each). Here's another solution that meets a primary objective of both being clear and working across all systems, on all bash (no assumptions about bash versions, or readlink or pwd options), and reasonably does what you'd expect to happen (eg, resolving symlinks is an interesting problem, but isn't usually what you actually want), handle edge cases like spaces in paths, etc., ignores any errors and uses a sane default if there are any issues.
每个组件都存储在一个单独的变量中,您可以单独使用:
# script path, filename, directory
PROG_PATH=${BASH_SOURCE[0]} # this script's name
PROG_NAME=${PROG_PATH##*/} # basename of script (strip path)
PROG_DIR="$(cd "$(dirname "${PROG_PATH:-$PWD}")" 2>/dev/null 1>&2 && pwd)"
BASE_DIR="$(cd "$(dirname "$0")"; pwd)";
echo "BASE_DIR => $BASE_DIR"
推荐文章
- 查看PS命令的全部输出
- 确保一次只运行一个shell脚本实例的快速方法
- 如何从命令行通过mysql运行一个查询?
- 在创建守护进程时执行双fork的原因是什么?
- 如何在Makefile中设置子进程的环境变量
- 如何让“wc -l”打印没有文件名的行数?
- 有效地测试Linux上的端口是否打开?
- 如何从另一个文件A中删除文件B中出现的行?
- 对以制表符分隔的文件进行排序
- Shell脚本删除超过n天的目录
- 如何检查shell脚本中是否存在命令?
- 如何使用查找命令从列表中查找所有具有扩展名的文件?
- 如何打破一个循环在Bash?
- 如何将文件指针(file * fp)转换为文件描述符(int fd)?
- 如何合并2 JSON对象从2个文件使用jq?