2011-07-10 29 views
36

如何将路径名中的..转换为bash脚本中的绝对路径名。也就是说,如果我有一条路径/home/nohsib/dvc/../bop,我希望将其更改为无点的路径,在这种情况下,/home/nohsib/bop如何将路径名中的“..”转换为bash脚本中的绝对名称?

我该怎么做?

+2

@Tony : 回覆。你的mod:''..''不是省略号。它只有两个点...一个点代表当前目录,两个点代表父代。省略号表示不确定的范围。 ''..''是非常具体的。 [省略(编程操作员)](http://en.wikipedia.org/wiki/Ellipsis_%28programming_operator%29) –

+0

@fred - 谢谢,不知道我在那里想什么。我只能说,编辑SO问题已经很晚了,为时已晚。我睡觉了。 – Tony

+0

这可能属于Unix堆栈交换站点... – jth41

回答

40

你在找什么是readlink

absolute_path=$(readlink -m /home/nohsib/dvc/../bop) 

请注意:您需要使用GNU的readlink实现它提供了 “-m” 选项。例如BSD的readlink没有。

+2

比cd更棒! pwd'解决方案。值得注意的是相关的C函数是'realpath(3)'。 –

+1

这不是100%可移植的,但应该适用于大多数Linux系统 – Daenyth

+8

这是不正确的答案。 SO不需要将符号链接解析为实际路径,但将相对路径扩展为绝对路径,这是不同的事情。假设我有数据文件和符号链接到目录中的脚本,如果要解析当使用符号链接的相对路径时目录的绝对路径,以便我要访问数据文件,readlink或实际路径将失败 –

29

尝试:

ABSOLUTE_PATH=$(cd /home/nohsib/dvc/../bop; pwd) 
+3

我认为这个答案应该在顶部。有用。它是跨平台的,不同于在OS X上有问题的readlink解决方案。 – algal

+0

这只适用于目录路径,而不适用于文件路径。 –

+4

@Craig:'ABSOLUTE_PATH = $(cd $(dirname {dir或file}); pwd)' –

2

使用

echo Absolute path: $(cd $1; pwd) 
-1

试试这个(假设你的相对路径存储在变量$ rel_path):

echo "`cd $rel_path; pwd`" 
+2

您执行pwd,捕获它的输出,然后使用echo打印它?不,谢谢,只需运行pwd而没有反引号并且没有回声(基本上它们相互抵消)。 –

1

只是一个额外的注意,如果您当前的路径是一个符号链接下,你可以解决这个真实路径:

pwd -P 

为了解决您的具体问题,这将发出一个cd命令更改目录没有'..'的路径在里面。注意:您将在同一文件夹,只要使用正确的路径:

cd `pwd -P` 
0

作为替代GNU的的readlink和真实路径,我所创造的功能,以及将在脚本中独立的像PWD和东西外部命令的运行。

http://www.linuxquestions.org/questions/blog/konsolebox-210384/getting-absolute-paths-of-unix-directories-and-filenames-in-shell-scripts-3956/

其中之一是这一个。它会将绝对路径保存为$ __。我使用阅读那里是安全的路径名扩展。一个shell下

function getabspath { 
    local -a T1 T2 
    local -i I=0 
    local IFS=/ A 

    case "$1" in 
    /*) 
     read -r -a T1 <<< "$1" 
     ;; 
    *) 
     read -r -a T1 <<< "/$PWD/$1" 
     ;; 
    esac 

    T2=() 

    for A in "${T1[@]}"; do 
     case "$A" in 
     ..) 
      [[ I -ne 0 ]] && unset T2\[--I\] 
      continue 
      ;; 
     .|'') 
      continue 
      ;; 
     esac 

     T2[I++]=$A 
    done 

    case "$1" in 
    */) 
     [[ I -ne 0 ]] && __="/${T2[*]}/" || __=/ 
     ;; 
    *) 
     [[ I -ne 0 ]] && __="/${T2[*]}" || __=/. 
     ;; 
    esac 
} 
0

一个很好的解决办法是:

readlink -ev mypathname 

它打印出与解决点的全路径名。使用

7

一个问题:

ABSOLUTE_PATH=$(cd ${possibleDirectory}; pwd)

是,如果$ {} possibleDirectory不存在,ABSOLUTE_PATH将被设置为当前目录。这可能不是你想要或期望的。

我想用这个版本可能是一般更可取:

ABSOLUTE_PATH=$(cd ${possibleDirectory} && pwd)

如果$ {possibleDirectory}不存在或无法访问,由于缺少目录的访问权限,ABSOLUTE_PATH将包含空串。

这样做的好处是您可以测试空字符串或根据具体情况自然地尝试失败。默认为一个失败的“CD”命令的情况下,当前目录可能会导致非常意外,并可能导致灾难性的后果(如RM -rf“$ ABSOLUTE_PATH”)

+0

这只适用于目录路径,不适用于文件路径。 –

3

如果你想这样做,而不遵循任何符号链接,然后尝试使用realpath与选项-s

$ realpath -s /home/nohsib/dvc/../bop 
/home/nohsib/bop 

注意与realpath,通常所有,但最后一个组件必须存在。因此,对于上述工作,下面都必须存在于文件系统:

/home 
/home/nohsib 
/home/nohsib/dvc 

但是你可以使用-m选项绕过的要求。

$ realpath -sm /home/nohsib/dvc/../bop 
/home/nohsib/bop 

(注realpath并不适用于所有的系统,尤其是老年人非Debian系统。对于那些在嵌入式Linux工作,遗憾的是Busybox的realpath不支持-s-m开关。)

相关问题