1. 程式人生 > >day5-shutil模塊

day5-shutil模塊

ash itl 作文 空目錄 絕對路徑 對象 分享圖片 zipfile dst

一、概述

我們通過python操作文件時,除正常讀寫操作外,有時還需要進行拷貝、刪除、打包等操作,雖然os模塊提供了部分功能,但還是不夠完善,這裏要講講專業的高級的文件,文件夾,壓縮包處理模塊shutil了。

二、shutil模塊常見用法

  • shutil.copyfileobj(fsrc, fdst,length)
    將源文件內容拷貝到目標文件中,因此涉及到文件的讀寫操作。查閱資料顯示可以拷貝部分文件內容,具體用法不詳,後續再研究把。
      1 import shutil
      2 with open(‘./binlog.log‘, ‘r‘, encoding=‘utf-8‘) as f1,  3     open
    (‘3.txt‘, ‘w‘, encoding=‘utf-8‘) as f2: 4 shutil.copyfileobj(f1, f2)
  • shutil.copyfile(src, dst)
    拷貝文件對象,但不包括權限
      1 shutil.copyfile(‘./1.txt‘,‘./2.txt‘)
      2 shutil.copyfile(‘./1.txt‘, ‘../2.txt‘)
  • shutil.copy(src, dst)
    拷貝文件,包括文件的權限(但不包括所有者屬性)
      1 >>> import os,shutil
      2 >>> os.chdir(‘/root/temp‘)
      3
    >>> shutil.copy(‘./test.py‘, ‘./2.py‘) 4 >>> quit() 5 [root@test210 temp]# ls -ltr 6 total 24 7 drwxr-xr-x. 4 root root 4096 Aug 23 14:21 DNS 8 drwxr-xr-x. 3 root root 4096 Nov 14 17:37 01 9 -rw-r--r--. 1 root root 7071 Nov 14 17:40 dns.zip 10 -rw-r--r--. 1 admin admin 23 Dec 26 07:49 test.py 11
    -rw-r--r--. 1 root root 23 Dec 26 07:54 2.py # 拷貝的文件權限與源文件一致,但所有者不同
  • shutil.copymode(src,dst)
    僅僅拷貝文件的權限,前提是dst文件存在,不然會報錯
      1 [root@test210 admin]# ls -ltr
      2 total 4
      3 -rwxr-xr-x. 1 admin admin 5 Jan  1 08:06 src_file
      4 -rw-r--r--. 1 root  root  0 Jan  1 08:08 dst_file  #初始文件權限不同
      5 [root@test210 admin]# python
      6 Python 2.6.6 (r266:84292, Jul 23 2015, 15:22:56)
      7 [GCC 4.4.7 20120313 (Red Hat 4.4.7-11)] on linux2
      8 Type "help", "copyright", "credits" or "license" for more information.
      9 >>> import os,shutil
     10 >>> os.chdir("/home/admin")
     11 >>> shutil.copymode(‘src_file‘,‘dst_file‘)
     12 >>> quit()
     13 [root@test210 admin]# ls -ltr
     14 total 4
     15 -rwxr-xr-x. 1 admin admin 5 Jan  1 08:06 src_file
     16 -rwxr-xr-x. 1 root  root  0 Jan  1 08:08 dst_file  #拷貝後文件權限相同
     17 [root@test210 admin]#
  • shutil.copystat(src,dst)
    拷貝文件的屬性狀態信息,如權限,各種時間,bit,flag等,但不包括所有者和所屬組
      1 [root@test210 temp]# ls -ltr
      2 total 24
      3 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
      4 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
      5 -rw-r--r--. 1 root  root  7071 Nov 14 17:40 dns.zip
      6 -rw-r--r--. 1 admin admin   23 Dec 26 07:49 test.py
      7 -rwxr-xr-x. 1 root  root    23 Dec 26 07:54 2.py
      8 [root@test210 temp]# python
      9 Python 2.6.6 (r266:84292, Jul 23 2015, 15:22:56)
     10 [GCC 4.4.7 20120313 (Red Hat 4.4.7-11)] on linux2
     11 Type "help", "copyright", "credits" or "license" for more information.
     12 >>> import os,shutil
     13 >>> os.chdir(‘/root/temp‘)
     14 >>> os.stat(‘test.py‘)
     15 posix.stat_result(st_mode=33188, st_ino=1309341, st_dev=64768L, st_nlink=1, st_uid=500, st_gid=500, st_size=23, st_atime=1514246087, st_mtime=1514245766, st_ctime=1514246037)
     16 >>> os.stat(‘2.py‘)
     17 posix.stat_result(st_mode=33261, st_ino=1308211, st_dev=64768L, st_nlink=1, st_uid=0, st_gid=0, st_size=23, st_atime=1514246087, st_mtime=1514246087, st_ctime=1514765789)
     18 >>> shutil.copystat(‘test.py‘,‘2.py‘)
     19 >>> quit()
     20 [root@test210 temp]# ls -ltr
     21 total 24
     22 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
     23 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
     24 -rw-r--r--. 1 root  root  7071 Nov 14 17:40 dns.zip
     25 -rw-r--r--. 1 root  root    23 Dec 26 07:49 2.py
     26 -rw-r--r--. 1 admin admin   23 Dec 26 07:49 test.py  #拷貝後2.py和test.py除所有者和所屬組不同外,其他常見屬性相同
  • shutil.copy2(src,dst)
    拷貝文件和文件的屬性狀態,目前來看等同於cp -a或cp -p
      1 [root@test210 temp]# ls -ltr
      2 total 24
      3 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
      4 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
      5 -rw-r--r--. 1 root  root  7071 Nov 14 17:40 dns.zip
      6 -rw-r--r--. 1 root  root    23 Dec 26 07:49 2.py
      7 -rw-r--r--. 1 admin admin   23 Dec 26 07:49 test.py
      8 [root@test210 temp]#
      9 [root@test210 temp]#
     10 [root@test210 temp]# python
     11 Python 2.6.6 (r266:84292, Jul 23 2015, 15:22:56)
     12 [GCC 4.4.7 20120313 (Red Hat 4.4.7-11)] on linux2
     13 Type "help", "copyright", "credits" or "license" for more information.
     14 >>> import os,shutil
     15 >>> os.chdir(‘/root/temp‘)
     16 >>> shutil.copy2(‘2.py‘,‘3.py‘)
     17 >>> quit()
     18 [root@test210 temp]# ls -ltr
     19 total 28
     20 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
     21 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
     22 -rw-r--r--. 1 root  root  7071 Nov 14 17:40 dns.zip
     23 -rw-r--r--. 1 root  root    23 Dec 26 07:49 3.py
     24 -rw-r--r--. 1 root  root    23 Dec 26 07:49 2.py
     25 -rw-r--r--. 1 admin admin   23 Dec 26 07:49 test.py
     26 [root@test210 temp]# cp -a 2.py 4.py
     27 [root@test210 temp]# ls -ltr
     28 total 32
     29 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
     30 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
     31 -rw-r--r--. 1 root  root  7071 Nov 14 17:40 dns.zip
     32 -rw-r--r--. 1 root  root    23 Dec 26 07:49 4.py
     33 -rw-r--r--. 1 root  root    23 Dec 26 07:49 3.py
     34 -rw-r--r--. 1 root  root    23 Dec 26 07:49 2.py
     35 -rw-r--r--. 1 admin admin   23 Dec 26 07:49 test.py
     36 [root@test210 temp]# cp -p 2.py 5.py
     37 [root@test210 temp]# ls -ltr
     38 total 36
     39 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
     40 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
     41 -rw-r--r--. 1 root  root  7071 Nov 14 17:40 dns.zip
     42 -rw-r--r--. 1 root  root    23 Dec 26 07:49 5.py
     43 -rw-r--r--. 1 root  root    23 Dec 26 07:49 4.py
     44 -rw-r--r--. 1 root  root    23 Dec 26 07:49 3.py
     45 -rw-r--r--. 1 root  root    23 Dec 26 07:49 2.py
     46 -rw-r--r--. 1 admin admin   23 Dec 26 07:49 test.py
  • shutil.copytree(src,dst)
    遞歸拷貝文件,相當於cp -r
      1 [root@test210 temp]# ls -ltr
      2 total 36
      3 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
      4 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
      5 [root@test210 temp]# python
      6 Python 2.6.6 (r266:84292, Jul 23 2015, 15:22:56)
      7 [GCC 4.4.7 20120313 (Red Hat 4.4.7-11)] on linux2
      8 Type "help", "copyright", "credits" or "license" for more information.
      9 >>> import os,shutil
     10 >>> os.chdir(‘/root/temp‘)
     11 >>> shutil.copytree(‘01‘,‘02‘)
     12 >>> quit()
     13 [root@test210 temp]# ls -ltr 01 02
     14 02:
     15 total 4
     16 drwxr-xr-x. 4 root root 4096 Aug 23 14:21 DNS
     17 
     18 01:
     19 total 4
     20 drwxr-xr-x. 4 root root 4096 Aug 23 14:21 DNS
     21 [root@test210 temp]# ls -ltr
     22 total 40
     23 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
     24 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 02
     25 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
  • shutil.rmtree(path[, ignore_errors[, onerror]])
    遞歸刪除文件,相當於rm -rf
      1 [root@test210 temp]# ls -ltr
      2 total 40
      3 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
      4 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 02
      5 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
      6 [root@test210 temp]# pyhon
      7 -bash: pyhon: command not found
      8 [root@test210 temp]# python
      9 Python 2.6.6 (r266:84292, Jul 23 2015, 15:22:56)
     10 [GCC 4.4.7 20120313 (Red Hat 4.4.7-11)] on linux2
     11 Type "help", "copyright", "credits" or "license" for more information.
     12 >>> import os,shutil
     13 >>> os.chdir(‘/root/temp‘)
     14 >>> shutil.rmtree(‘02‘)
     15 >>> quit()
     16 [root@test210 temp]# ls -ltr
     17 total 36
     18 drwxr-xr-x. 4 root  root  4096 Aug 23 14:21 DNS
     19 drwxr-xr-x. 3 root  root  4096 Nov 14 17:37 01
  • shutil.move(src,dst)
    移動文件,如果是路徑則遞歸移動,相當於mv
      1 [root@test210 temp]# ls -ltr
      2 total 20
      3 drwxr-xr-x. 4 root root 4096 Aug 23 14:21 DNS
      4 drwxr-xr-x. 3 root root 4096 Nov 14 17:37 01
      5 -rw-r--r--. 1 root root 7071 Nov 14 17:40 dns.zip
      6 drwxr-xr-x. 2 root root 4096 Jan  1 08:32 02
      7 [root@test210 temp]# ls -ltr 02
      8 total 0
      9 [root@test210 temp]# python
     10 Python 2.6.6 (r266:84292, Jul 23 2015, 15:22:56)
     11 [GCC 4.4.7 20120313 (Red Hat 4.4.7-11)] on linux2
     12 Type "help", "copyright", "credits" or "license" for more information.
     13 >>> import os,shutil
     14 >>> os.chdir(‘/root/temp‘)
     15 >>> shutil.move(‘dns.zip‘,‘02‘)
     16 >>> shutil.move(‘01‘,‘02‘)
     17 >>> quit()
     18 [root@test210 temp]# ls -ltr
     19 total 8
     20 drwxr-xr-x. 4 root root 4096 Aug 23 14:21 DNS
     21 drwxr-xr-x. 3 root root 4096 Jan  1 08:34 02
     22 [root@test210 temp]# ls -ltr 02
     23 total 12
     24 drwxr-xr-x. 3 root root 4096 Nov 14 17:37 01
     25 -rw-r--r--. 1 root root 7071 Nov 14 17:40 dns.zip

三、shutil模塊常見用法

1. shutil.make_archive((base_name, format, root_dir=None,base_dir=None,verbose=0,dry=0,owner=None,group=None,logger=None)

功能:創建壓縮包並且返回文件路徑,例如:zip,tar

  • base_name : 壓縮包的文件名,也可以是壓縮包的路徑,或者路徑加文件名的混合體。如果僅僅指定文件名,則保存在當前目錄,否則保存到指定路徑。如果僅僅指定路徑或者指定了路徑和文件名,則自動把最後一級目錄(如果只有路徑)或者文件名作為壓縮包的文件名前綴來處理。
  • format:壓縮包種類,‘zip‘,‘tar‘,‘bztar‘,‘gztar‘
  • root_dir:需要壓縮的文件夾路徑(默認當前路徑)
  • owner:用戶,默認當前用戶
  • group:組,默認當前組
  • logger:用於記錄日誌,通常是logging.Logger對象
      1 >>> import shutil
      2 >>> shutil.make_archive(‘jb51.net‘,‘zip‘,"C:/Users/Beyondi/Downloads/jb51.net")
      3 ‘C:\\Users\\Beyondi\\jb51.net.zip‘  #壓縮包的保存路徑是cmd的默認路徑
      4 >>>
      5 >>>
      6 >>> shutil.make_archive(‘C:/Users/Beyondi/Downloads/jb51.net‘,‘zip‘,"C:/Users/Be
      7 yondi/Downloads/jb51.net")
      8 ‘C:\\Users\\Beyondi\\Downloads\\jb51.net.zip‘  #指定了路徑和文件名
      9 >>> shutil.make_archive(‘C:/Users/Beyondi/Downloads/‘,‘zip‘,"C:/Users/Beyondi/Do
     10 wnloads/jb51.net")
     11 ‘C:\\Users\\Beyondi\\Downloads.zip‘ #僅僅指定路徑,最後一級路徑就被自動作為壓縮包的文件名了
     12 >>>


2. zipfile模塊

功能:以zip的形式壓縮和解壓縮文件,註意了這個只能壓縮文件,不能壓縮目錄,如果壓縮,也只能顯示空目錄。

  1 >>> import zipfile
  2 #壓縮
  3 >>> z=zipfile.ZipFile(‘test.zip‘, ‘w‘)
  4 >>> z.write(‘test.txt‘)
  5 >>> z.close()
  6 
  7 #解壓縮
  8 >>> z=zipfile.ZipFile(‘test.zip‘,‘r‘)
  9 >>> z.extractall()
 10 >>> z.close
 11 
 12 #操作方法類似於文件的操作


3. tarfile模塊

功能:以tar的形式打包文件,能打包一切形式的文件,包括目錄

  • 打包

打包通過tar.add來實現,語法:先以寫的方式打開tarfile文件對象,然後是tar.add(‘file’, arcname=’’), 第一個參數是期望打包的文件(可以是目錄),第二個參數可選,定義打包文件中被打包文件的名稱,如果不寫則自動采用第一個參數的文件名,但會去掉根路徑(猜測與Linux下的tar類似,防止解壓後覆蓋根路徑下的重要文件)

  1 >>> import tarfile
  2 >>> tar = tarfile.open(‘test.tar‘,‘w‘)
  3 >>> tar.add(‘test.zip‘)
  4 >>> tar.add(‘C:/Users/Beyondi/Downloads/jb51.net‘,arcname=‘jb51.net‘)
  5 >>> tar.add(‘E:/test/site.yml‘)
  6 >>> tar.close()
  7 >>>

來看下打包的效果:

技術分享圖片技術分享圖片

通過上圖可看到,沒有定義打包文件中的文件名的,文件名就是源文件名,包含絕對路徑,但已經去掉了根路徑


  • 解壓

解壓通過tar.extractall() 來實現,可自定義解壓後的路徑,默認就是當前目錄。當然前提是先以讀的方式打開tarfile文件對象。

  1 >>> import tarfile
  2 >>> tar=tarfile.open(‘test.tar‘,‘r‘)
  3 >>> tar.extractall(‘tartest‘) #解壓到指定目錄下
  4 >>> tar.close()

解壓後的效果:

技術分享圖片

可以看到解壓後的文件形式與在tar包中直接打開看到的相同。

day5-shutil模塊