您可以輕鬆地在
print path, dirs, files
右下方
for path, dirs, files in os.walk(src, topdown=True):
本質上診斷這個,你遞歸兩次。
本身,os.walk
下降到子目錄。通過遞歸調用你自己的函數,你會雙降序。下面是從print
聲明瞭一些輸出示例:
>>> copy_file("c:\Intel", "c:\Intel-Bak")
c:\Intel ['ExtremeGraphics', 'Logs'] []
c:\Intel\ExtremeGraphics ['CUI'] []
c:\Intel\ExtremeGraphics\CUI ['Resource'] []
c:\Intel\ExtremeGraphics\CUI\Resource [] ['Intel\xae Graphics and Media Control Panel.lnk', 'Intel\xae HD Graphics.lnk']
c:\Intel\ExtremeGraphics\CUI\Resource [] ['Intel\xae Graphics and Media Control Panel.lnk', 'Intel\xae HD Graphics.lnk']
c:\Intel\ExtremeGraphics\CUI ['Resource'] []
c:\Intel\ExtremeGraphics\CUI\Resource [] ['Intel\xae Graphics and Media Control Panel.lnk', 'Intel\xae HD Graphics.lnk']
c:\Intel\ExtremeGraphics\CUI\Resource [] ['Intel\xae Graphics and Media Control Panel.lnk', 'Intel\xae HD Graphics.lnk']
c:\Intel\Logs [] ['IntelChipset.log', 'IntelControlCenter.log', 'IntelGFX.log', 'IntelGFXCoin.log']
c:\Intel\ExtremeGraphics ['CUI'] []
c:\Intel\ExtremeGraphics\CUI ['Resource'] []
c:\Intel\ExtremeGraphics\CUI\Resource [] ['Intel\xae Graphics and Media Control Panel.lnk', 'Intel\xae HD Graphics.lnk']
c:\Intel\ExtremeGraphics\CUI\Resource [] ['Intel\xae Graphics and Media Control Panel.lnk', 'Intel\xae HD Graphics.lnk']
c:\Intel\ExtremeGraphics\CUI ['Resource'] []
c:\Intel\ExtremeGraphics\CUI\Resource [] ['Intel\xae Graphics and Media Control Panel.lnk', 'Intel\xae HD Graphics.lnk']
c:\Intel\ExtremeGraphics\CUI\Resource [] ['Intel\xae Graphics and Media Control Panel.lnk', 'Intel\xae HD Graphics.lnk']
c:\Intel\Logs [] ['IntelChipset.log', 'IntelControlCenter.log', 'IntelGFX.log', 'IntelGFXCoin.log']
正如你所看到的,目錄訪問得到兩次。
你應該修改你的程序的邏輯,因此訪問每個目錄只有一次,但理論上你可以不理會你已經去過任何目錄:
visited = []
def copy_file(src, dest):
for path, dirs, files in os.walk(src, topdown=True):
if path not in visited:
for di in dirs:
print dest, di
copy_file(join(path, di), join(dest, di))
if not exists(dest):
os.makedirs(dest)
for fi in files:
shutil.copy(join(path, fi), dest)
visited.append(path)
來源
2012-04-11 17:00:19
agf
謝謝。但我有另一個問題。當我讀到os.walk()的文檔時,他們說:「當topdown爲True時,調用者可以就地修改dirnames列表(可能使用del或slice賦值),而walk()只會遞歸到子目錄中名字保留在dirnames中;「 – linuxlsx 2012-04-12 02:06:11
@linuxlsx對。通過遍歷'dirs'並刪除其中的每個目錄,您將其保留爲空。所以'os.walk'根本不會下降 - 唯一的訪問是通過遞歸調用完成的。你已經把'os.walk'變成了一個奇特的'os.listdir'。我不確定你的意思是「爲什麼它工作」。 – agf 2012-04-12 02:37:28