0

这是一个微妙的问题,我知道,但我希望你能忍受我片刻。

假设/tmp/dir是一个符号链接到/home/user/some/dir. 还假设您当前的工作目录是/tmp/dir.

即使扩展类似的东西.似乎也不可能,因为os.getcwd()返回/home/user/some/dir而不是/tmp/dir命令pwd返回的内容。相对目录也可以是../dir/../dir/subdir,.././././dir/foo等。

所以我的问题是:是否有任何可靠的函数可以对相对路径进行路径扩展但不遵循相对路径中可能存在的符号链接。例如,如果是../dir/../dir/subdir,我想得到/tmp/dir/subdir而不是/home/user/some/dir/subdir

只是为了避免得到我不想要的东西,答案是 NOT os.path.abspath, os.path.realpath, os.path.expanduser, or os.path.relpath

4

2 回答 2

1

似乎您不是第一个注意到chdir(2).

Linux 联机帮助页中没有关于它的内容,但类似的页面说...

int chdir(const char *path);

[...]

chdir()函数使由path命名的目录成为新的当前目录。如果path的最后一个组件是符号链接,则 chdir()解析符号链接的内容。如果chdir()函数失败,则当前目录不变。

...尽管没有解释为什么它会解析符号链接。

因此,从技术上讲,您不能拥有 的当前工作目录/tmp/dir,即使您的 shell 另有声明也是如此。

但是,您可以利用 shell 的内置cd命令将环境变量设置PWD为您输入的值这一事实,因此您可以这样做...

$ cd /tmp/dir
$ python
>>> import os
>>> os.getcwd()
'/home/user/some/dir'
>>> os.environ['PWD']
'/tmp/dir'
>>> os.path.normpath(os.path.join(os.environ['PWD'], '../dir/../dir/subdir'))
'/tmp/dir/subdir'

...尽管在进程不是从 shell 启动的情况下它可能会失败。

于 2013-06-22T17:39:55.143 回答
0

不确定那是您要查找的内容,但是...您可以编写一个函数,从相对路径和当前工作目录生成“逻辑”完整路径,然后检查生成的路径是否确实存在于系统上。该函数可能如下所示:

import os

def absolute_path(path):
    wd = os.getcwd()
    full = os.path.join(wd, path)

    parts = full.split(os.sep)
    kept = []
    skip = 0
    for part in reversed(parts):
        if part == '..':
            skip += 1
        elif skip == 0:
            kept.insert(0, part)
        else:
            skip -= 1
    return os.sep + os.path.join(*kept)
于 2013-06-22T16:44:00.527 回答