Python 常見檔案 / 資料夾操作
Posted on Dec 13, 2018 in Python 程式設計 - 初階 by Amo Chen ‐ 2 min read
年紀越大越容易金魚腦發作,有些東西不記錄成文章就特別容易忘。
本文記錄 Python 幾種常用的檔案(包含壓縮檔)與資料夾操作,以供速查之用。
本文環境
- python 3.6.5
- requests 2.19.1
下載檔案
程式內會需要透過 HTTP 下載檔案進行處理,這時候可以用 requests 模組下載檔案,然後將檔案的內容(content)直接寫入到檔案中:
import os
import requests
resp = requests.get(url)
file_path = os.path.join('/tmp', os.path.basename(url))
with open(file_path, 'wb') as file:
file.write(resp.content)
解壓縮 ZIP 檔
如果下載的檔案是個 ZIP 壓縮檔,可以用 Zipfile 模組進行解壓縮:
import os
from zipfile import ZipFile
unzip_dir = os.path.join('/tmp', 'unzip')
os.mkdir(unzip_dir)
with ZipFile(zip_filename) as zip_ref:
print(zip_ref.namelist())
zip_ref.extractall(unzip_dir)
上述範例 zip_ref.namelist()
會取得 ZIP 壓縮檔內的所有檔名,而 zip_ref.extractall(unzip_dir)
會將所有檔案解壓縮至 unzip_dir
資料夾內。
壓縮檔案
通常使用 AWS 等雲端服務,頻寬的使用也是收費的一環,所以透過網路傳輸檔案時不免要壓縮一下檔案,除了加速檔案傳輸外也可多少節省些頻寬花費,以下示範 ZIP 與 Tar.gz 2 種壓縮方式:
ZIP
from zipfile import ZipFile
with ZipFile('test.zip', 'w') as zip:
zip.write('test.txt')
ZipFile 也提供多種不同的壓縮方式可以選擇:
zipfile.ZIP_STORED
zipfile.ZIP_DEFLATED
zipfile.ZIP_BZIP2
zipfile.ZIP_LZMA
此外更可透過 compresslevel
設定壓縮等級,不過不同的壓縮方法有不一樣的級別設定,需特別注意:
The compresslevel parameter controls the compression level to use when writing files to the archive. When using ZIP_STORED or ZIP_LZMA it has no effect. When using ZIP_DEFLATED integers 0 through 9 are accepted (see zlib for more information). When using ZIP_BZIP2 integers 1 through 9 are accepted (see bz2 for more information).
設定不同壓縮方法與壓縮等級範例:
with ZipFile('test.zip', 'w', compression=zipfile.ZIP_BZIP2, compresslevel=9) as zip:
zip.write('test.txt')
Tar.gz
壓縮成 tar.gz 檔則是透過 tarfile 模組:
import tarfile
tar_gz = tarfile.open('sample.tar.gz', 'w:gz')
for name in ['test1.txt', 'test2.txt']:
tar_gz.add(name)
tar_gz.close()
跟 ZipFile 不一樣的是 tarfile 的 filemode
可以用冒號( :
)做為分隔並指定壓縮的演算法,例如上述的 w:gz
即是指用 gzip
方式進行壓縮。詳細請參閱 文件 。
建立資料夾
建立資料夾除了 os.mkdir 之外,還可以使用 os.makedirs :
import os
path = '/tmp/a/b/c'
os.makedirs(path)
makedirs 會幫忙將路徑中不存在的資料夾也一併建立,上述範例就相當於 Linux 指令:
$ mkdir -p /tmp/a/b/c
建立 temp 資料夾
有時候程式 concurrency 執行時,需要各自暫時的資料夾以彼此隔離避免檔案同時被讀取,導致無法預期的錯誤。此種情境可以使用 tempfile 模組為每個 process / thread 取得暫時性的資料夾:
import tempfile
temp_dir = tempfile.mkdtemp(prefix='temp')
print(temp_dir)
此外,使用上需要注意的是 mkdtemp 並不會主動刪除資料夾,因此程式結束之前需自行刪除這些資料夾。
The user of mkdtemp() is responsible for deleting the temporary directory and its contents when done with it.
刪除資料夾
刪除資料夾可以運用 shutil 模組提供的 rmtree
函示,該函式會遞迴刪除該資料夾底下的所有檔案:
import os
import shutil
path = '/tmp/a/b/c'
os.makedirs(path)
shutil.rmtree(path)
走訪資料夾
走訪資料夾的功能由 os.walk
函示所提供:
import os
from os.path import join, getsize
for root, dirs, files in os.walk('./your/path'):
print(root, dirs, files)
複製檔案
shutil 模組提供 2 種複製檔案的方式,分別為 shutil.copy 與 shutil.copy2 其差別在於 shutil.copy2
會保留檔案中的 meta 資料(例如 permission bits, last access time, last modification time 等等):
import shutil
src = '/etc/profile'
dst = '/tmp/profile.backup'
shutil.copy(src, dst)
# or
shutil.copy2(src, dst)
重新命名檔案 / 資料夾
範例:
import os
src = '/tmp/profile.backup'
dst = '/tmp/profile'
os.rename(src, dst)
刪除檔案
範例:
import os
path = '/tmp/file.txt'
file = open(path, 'wb')
file.close()
os.remove(path)
References
https://docs.python.org/3/library/tarfile.html
https://docs.python.org/3/library/zipfile.html
https://docs.python.org/3/library/tempfile.html
https://docs.python.org/3/library/shutil.html