クローラなどでWeb上の画像を収集する際に、「画像ファイル全部をダウンロードせずに、画像の大きさ(解像度)だけを得たい」という状況になることがあります。そこで、ファイルのヘッダさえ見れば、全てをダウンロードせずとも目的の情報を得られることが出来ます。
以下ソースコードです。Python 3.4.2 + OS X 10.10(Yosemite)で動作を確認しました。
GIF, JPEG, PNG フォーマットに対応しています。
なお、OpenCVなどの追加ライブラリは必要がありません。
import sys
import struct
import urllib.request
def parse_jpeg(res):
while not res.closed:
(marker, size) = struct.unpack('>2sH', res.read(4))
if marker == b'\xff\xc0':
(_,height,width,_) = struct.unpack('>chh10s', res.read(size-2))
return (width,height)
else:
res.read(size-2)
def parse_png(res):
(_,width,height) = struct.unpack(">14sII", res.read(22))
return (width, height)
def parse_gif(res):
(_,width,height) = struct.unpack("<4sHH", res.read(8))
return (width, height)
def get_image_size(url):
res = urllib.request.urlopen(url)
size = (-1,-1)
if res.status == 200:
signature = res.read(2)
if signature == b'\xff\xd8': #jpg
size = parse_jpeg(res)
elif signature == b'\x89\x50': #png
size = parse_png(res)
elif signature == b'\x47\x49': #gif
size = parse_gif(res)
res.close()
return size
エラー処理などは適宜補ってください。
参考資料
暗黒通信団『ファイルフォーマット小事典』(ISBN4-87310-064-X)