(1)打開文件
使用Python內置的open()
函數,傳入文件名和標示符,打開一個文件對象:
>>> import os
>>> f = open('/Users/michael/test.txt', 'r')
標示符'r'
表示讀,這樣,我們就成功地打開了一個文件。
Python引入了with
語句來避免程序出錯:
with open('/path/to/file', 'r') as f:
print(f.read())
上面的代碼相當於:
try:
f = open('/path/to/file', 'r')
print(f.read())
finally:
if f:
f.close()
(2)讀文件內容
(3)關閉文件
調用close()
方法關閉文件。文件使用完畢後必須關閉,因為文件對象會占用操作系統的資源。
>>> f.close()
(4)讀取其它編碼格式文件
要讀取二進制文件,比如圖片、視頻等等,用'rb'
模式打開文件即可:
>>> f = open('/Users/michael/test.jpg', 'rb')
>>> f.read()
b'\xff\xd8\xff\xe1\x00\x18Exif\x00\x00...' # 十六進制表示的字節
要讀取非UTF-8編碼的文本文件,需要給open()
函數傳入encoding
參數,例如,讀取GBK編碼的文件:
>> f = open('/Users/michael/gbk.txt', 'r', encoding='gbk')
>>> f.read()
'測試'
調用open()
,傳入標識符'w'
或者'wb'
表示寫文本文件或寫二進制文件:
>>> f = open('/Users/michael/test.txt', 'w')
>>> f.write('Hello, world!')
>>> f.close()
可以反復調用write()
來寫入文件,但是務必要調用f.close()
來關閉文件。當我們寫文件時,操作系統往往不會立刻把數據寫入磁盤,而是放到內存緩存起來,空閒的時候再慢慢寫入。只有調用close()
方法時,操作系統才保證把沒有寫入的數據全部寫入磁盤。
所以通常,還是使用with
語句寫文件:
with open('/Users/michael/test.txt', 'w') as f:
f.write('Hello, world!')
Python內置的os
模塊可以直接調用操作系統提供的接口函數。
(1)查看目錄
# 查看當前目錄的絕對路徑:
>>> os.path.abspath('.')
'/Users/michael'
(2)創建目錄
# 在某個目錄下創建一個新目錄,首先把新目錄的完整路徑表示出來:
>>> os.path.join('/Users/michael', 'testdir')
'/Users/michael/testdir'
# 然後創建一個目錄:
>>> os.mkdir('/Users/michael/testdir')
(3)刪除目錄
# 刪掉一個目錄:
>>> os.rmdir('/Users/michael/testdir')
(4)合並與拆分路徑
把兩個路徑合成一個時,不要直接拼字符串,而要通過os.path.join()
函數。
>>> os.path.join('/Users/michael', 'testdir')
'/Users/michael/testdir'
要拆分路徑時,也不要直接去拆字符串,而要通過os.path.split()
函數。
>>> os.path.split('/Users/michael/testdir/file.txt')
('/Users/michael/testdir', 'file.txt')
(5)獲取擴展名
os.path.splitext()
可以直接讓你得到文件擴展名:
>>> os.path.splitext('/path/to/file.txt')
('/path/to/file', '.txt')
(1)文件重命名
# 對文件重命名:
>>> os.rename('test.txt', 'test.py')
(2)文件刪除
# 刪掉文件:
>>> os.remove('test.py')
(3)復制與移動文件
os
模塊中並未提供復制與移動文件的函數,但shutil
模塊提供了copyfile()
的函數,可以看作是os
模塊的補充。
shutil.copy(src_file, target_path)
shutil.move(src_file, target_path)
import shutil
shutil.copy('/Users/michael/testdir1/file.txt', '/Users/michael/testdir2')
shutil.move('/Users/michael/testdir1/file.txt', '/Users/michael/testdir2')
要在不同的編程語言之間傳遞對象,就必須把對象序列化為標准格式,最常用的就是序列化為JSON。
因為JSON表示出來就是一個字符串,可以被所有語言讀取,也可以方便地存儲到磁盤或者通過網絡傳輸。JSON不僅是標准格式,並且比XML更快,而且可以直接在Web頁面中讀取,非常方便。
Python內置的json
模塊提供了非常完善的Python對象到JSON格式的轉換。我們先看看如何把Python對象變成一個JSON:
>>> import json
>>> d = dict(name='Bob', age=20, score=88)
>>> json.dumps(d)
'{"age": 20, "score": 88, "name": "Bob"}'
dumps()
方法返回一個str
,內容就是標准的JSON。dump()
方法可以直接把JSON寫入一個file-like Object
。
要把JSON反序列化為Python對象,用loads()
或者對應的load()
方法,前者把JSON的字符串反序列化,後者從file-like Object
中讀取字符串並反序列化:
>>> json_str = '{"age": 20, "score": 88, "name": "Bob"}'
>>> json.loads(json_str)
{
'age': 20, 'score': 88, 'name': 'Bob'}
由於通常情況下,我們會用class
表示對象,如果直接將對象序列化肯定會報錯,原因是Student
對象不是一個可序列化為JSON的對象。
import json
class Student(object):
def __init__(self, name, age, score):
self.name = name
self.age = age
self.score = score
s = Student('Bob', 20, 88)
print(json.dumps(s))
# 輸出
Traceback (most recent call last):
...
TypeError: <__main__.Student object at 0x10603cc50> is not JSON serializable
但,dumps()
方法還提供了一大堆的可選參數,其中可選參數default
就支持通過提供轉換函數,為dumps()
傳入對象實例以及轉換函數,就可以實現序列化。
精簡後的寫法如下:
print(json.dumps(s, default=lambda obj: obj.__dict__))
因為通常class
的實例都有一個__dict__
屬性,它就是一個dict
,用來存儲實例變量。
如果我們要把JSON反序列化為一個Student
對象實例,loads()
方法首先轉換出一個dict
對象,然後,我們傳入的object_hook
函數負責把dict
轉換為Student
實例:
def dict2student(d):
return Student(d['name'], d['age'], d['score'])
>>> json_str = '{"age": 20, "score": 88, "name": "Bob"}'
>>> print(json.loads(json_str, object_hook=dict2student))
<__main__.Student object at 0x10cd3c190>