如何在Python中获取文件的绝对路径?

2 投票
3 回答
4961 浏览
提问于 2025-04-18 06:45

我在这个网站上看了很多链接,大家都说要用“os.path.abspath(#文件名)”。不过这个方法对我来说并不是很有效。我正在写一个程序,目的是在指定的文件夹里搜索某些扩展名的文件,然后把文件名和它们的绝对路径分别存到一个字典里,最后用绝对路径打开这些文件,进行必要的修改。现在的问题是,当我使用os.path.abspath()时,它并没有返回完整的路径。

假设我的程序在桌面上。我有一个文件存储在“C:\Users\Travis\Desktop\Test1\Test1A\test.c”。我的程序可以很容易找到这个文件,但当我使用os.path.abspath()时,它返回的是“C:\Users\Travis\Desktop\test.c”,这是我源代码存储的绝对路径,而不是我想要找的那个文件的路径。

我的代码是:

import os
Files={}#Dictionary that will hold file names and absolute paths
root=os.getcwd()#Finds starting point
for root, dirs, files in os.walk(root):
    for file in files:
        if file.endswith('.c'):#Look for files that end in .c
            Files[file]=os.path.abspath(file)

有没有什么建议或者提示,为什么会这样,以及我该如何解决这个问题?谢谢!

3 个回答

-1

Glob在这些情况下很有用,你可以这样做:

files = {f:os.path.join(os.getcwd(), f) for f in glob.glob("*.c")}

这样可以得到相同的结果

0

根据os.path.join的文档

如果任何一个部分是绝对路径,那么之前的所有部分(在Windows上,包括之前的驱动器字母,如果有的话)都会被丢弃。

举个例子,如果第二个参数是一个绝对路径,那么第一个路径'/a/b/c'就会被丢掉。

In [14]: os.path.join('/a/b/c', '/d/e/f')
Out[14]: '/d/e/f'

因此,

os.path.join(root, os.path.abspath(file))

无论root是什么,都会被丢弃,并返回os.path.abspath(file),这个函数会把file加到当前工作目录上,而这个目录不一定和root是一样的。

如果想要形成文件的绝对路径:

fullpath = os.path.abspath(os.path.join(root, file))

其实,我认为os.path.abspath是多余的,因为我相信root总是绝对路径,但我的这个想法是基于os.walk的源代码,而不仅仅是os.walk文档中保证的行为。所以为了确保万无一失,还是用os.path.abspath吧。


import os
samefiles = {}
root = os.getcwd()
for root, dirs, files in os.walk(root):
    for file in files:
        if file.endswith('.c'):
            fullpath = os.path.join(root, file)
            samefiles.setdefault(file, []).append(fullpath) 

print(samefiles)
6

os.path.abspath() 这个函数的作用是把相对路径转换成绝对路径,但它是相对于当前工作目录的,而不是文件最初的位置。简单来说,路径就是一串字符,Python 并不知道这个文件名是从哪里来的。

你需要自己提供目录。当你使用 os.walk 时,每次循环都会列出当前正在查看的目录(在你的代码中是 root),还有子目录的列表(只是它们的名字)和文件名的列表(同样只是名字)。你可以把 root 和文件名结合起来,形成一个绝对路径:

Files={}
cwd = os.path.abspath(os.getcwd())
for root, dirs, files in os.walk(cwd):
    for file in files:
        if file.endswith('.c'):
            Files[file] = os.path.join(root, os.path.abspath(file))

需要注意的是,你的代码只记录每个独特文件名的 一个 路径;如果你有 foo/bar/baz.cfoo/spam/baz.c,那么哪个路径被记录下来取决于操作系统列出 barspam 子目录的顺序。

你可能想把路径收集到一个列表中:

Files={}
cwd = os.path.abspath(os.getcwd())
for root, dirs, files in os.walk(cwd):
    for file in files:
        if file.endswith('.c'):
            full_path = os.path.join(root, os.path.abspath(file))
            Files.setdefault(file, []).append(full_path)

撰写回答