python之成像庫pillow


python之成像庫pillow

python提供了python image library圖像庫,處理圖像功能,該庫提供了廣泛的文件格式支持,如JPEG、PNG、GIF、等,它提供了圖像檔案、圖像顯示、圖像處理等功能

PIL中所涉及到的基本概念包括,(bands)通道,(mode)模式,(coordinate system)坐標系統,(palette)調色板,(filters)過濾器

每張圖像都是由一個或者多個數據通道構成,PIL可以在單張圖片中合成相同維數和深度的多個通道,如RGB有三個通道,而灰度圖像則只有一個通道

圖像實際上是像素數據的矩形圖,圖像的模式定義了圖像中像素的類型和深度,它在圖像中定義mode模式的概念,如:

  • 1:1位像素,表示黑和白,占8bit,在圖像表示中稱為位圖
  • L:表示黑白之間的灰度,占8bit像素
  • p:8位像素,使用調色版映射
  • RGB:為真彩色,占用3x8位像素,其中R為red紅色,G為green綠色,B為blue藍色,三原色疊加形成的色彩變化,如三通道都為0則代表黑色,都為255則代表白色
  • RGBA:為帶透明蒙版的真彩色,其中的A為alpha透明度,占用4x8位像素

其他的還有打印分色CMYK不是很常用不多做介紹

PIL使用笛卡爾像素坐標系統,圖像的坐標從左上角開始(0,0),坐標值表示像素的角,它實際上位於(0.5,0.5);python中坐標通常以2元組(X,Y)的形式傳遞,矩形表示為4元組(l_x,t_y,r_x,b_y),X軸從左到右,Y軸從上到下,順序是從左上右下表示,從左上角開始,如一個800X600像素的圖像矩形表示為(0,0,800,600),它實際上時左上角鎖定,向右下延伸的。

PIL的安裝:

pip3 install pillow

官方文檔

pillow官方文檔

圖像模塊(Image.Image)

圖像模塊提供PIL名稱的類,該模塊提供了許多功能,包括文件加載和創建新圖像等,下面我們創建一個圖像對象,然后旋轉圖像90度並顯示:

from PIL import Image

im=Image.open("78525.jpg")
im.rotate(90).show()

批量創建縮略圖腳本,在文件夾下批量創建128x128的縮略圖:

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time    : 2018/7/9 16:40
# @Author  : Py.qi
# @File    : test1.py
# @Software: PyCharm
from PIL import Image
import glob,os

size=128,128
for infile in glob.glob('D:\image\*.jpg'):
    filename=os.path.split(infile)[-1]
    im=Image.open(infile)
    im.thumbnail(size,Image.ANTIALIAS)
    im.save("E:\images\\"+filename)   #注意保存圖像時按照比例縮放保存的,以最大像素為依據比例縮小

Image模塊的功能

Image.new(mode,size,color):

使用給定的模式、大小和顏色創建新圖像;大小以(寬度,高度)2 元組的形式給出,以像素為單位;顏色以單波段圖像的單個值和多波段圖像的元組(每個波段的一個值)給出,可以使用顏色名如‘red’也可以受用16進制#FF0000或者使用數字表示(255,0,0)

from PIL import Image

#這三種效果一樣,都為分辨率1920x1080的紅色圖像
im = Image.new('RGB',(1920,1080),(255,0,0))
im1 = Image.new('RGB',(1920,1080),'red')
im2 = Image.new('RGB',(1920,1080),'#FF0000')
im.show()
im1.show()
im2.show()

Image.open(file,mode):

讀取圖像文件頭,mode只能是‘r’

from PIL import Image
from io import BytesIO
import requests

#打開文件或從文件流中打開圖像
im=Image.open('path/to/imagefile.jpg')
r=requests.get('http://image.jpg')
im1=Image.open(BytesIO(r.content))
from PIL import Image

#將圖像轉換為PNG
im=Image.open('images/22.jpg','r')
im.save('images/33.png')
#im.show()
im_png=Image.open('images/33.png','r')
print(im_png.format)

#
PNG

Image.blend(image1,image2,alpha):

通過使用常量alpha在給定圖像之間進行差值來創建新圖像,兩個圖像必須具有相同的大小和模式,aplha為0則返回第一張圖像的拷貝,為1則返回第二張圖像的拷貝,可以去中間值來划分偏差如0.5

from PIL import Image

image1=Image.new('RGB',(1920,1080),(0,0,255))  #藍色圖像
image2=Image.new('RGB',(1920,1080),(255,0,0))  #紅色圖像
im=Image.blend(image1,image2,0.5)  #取中間值
image1.show()
image2.show()
im.show()  #顯示紫色圖像,因為紅色疊加藍色會調和成紫色
im.save('5555.jpg')

Image.composite(image1,image2,mask):

通過給定的圖像之間進行差值,使用mask圖像的響應像素作為alpha來創建新圖像,mask可以具有的模式‘1’,‘L’,或者‘RGBA’

image1=Image.new('RGB',(1920,1080),(0,0,255))  #藍色圖像
image2=Image.new('RGB',(1920,1080),(255,0,0))  #紅色圖像
image3=Image.new('L',(1920,1080),125)  #灰色

im=Image.composite(image1,image2,mask=image3)
image1.show()
image2.show()
image3.show()
im.show() 
im.save('5555.jpg')   

Image.eval(image,function):

function為接受一個整數參數的函數,將im的每個像素值分別傳給func處理並返回最后的Image對象

from PIL import Image

im = Image.open('31.gif')
evl = Image.eval(im,lambda x:x/2)  #將每個像素除以2
evl.show()

Image.merge(mode,bands):

從多個單通道創建新圖像,bands為圖像的元組或列表

from PIL import Image

im1=Image.open('1.jpg').resize((1024,768),Image.ANTIALIAS) #type:Image.Image
im2=Image.open('2.jpg').resize((1024,768),Image.ANTIALIAS) #type:Image.Image
im3=Image.open('5555.jpg').resize((1024,768),Image.ANTIALIAS) #type:Image.Image
im1_rgb=im1.split()
im2_rgb=im2.split()
im3_rgb=im3.split()
rgbs=[im1_rgb[0],im2_rgb[1],im3_rgb[2]] #使用三個圖像的單通道
im_merge=Image.merge('RGB',rgbs) #合成一張新圖像
im_merge.show()
print(im_merge.size,im_merge.mode)

Image模塊的方法

Image類的實例具有以下方法,所有方法都會返回Image類的新實例,並保留生成的圖像

im.convert(mode):

將圖像轉換為另一種模式,然后返回新圖像

from PIL import Image

image1=Image.open('1.jpg')
assert isinstance(image1,Image.Image)
img1=image1.convert('L')   #將圖像轉換為灰色
img1.show()

im.copy():拷貝圖像

im.crop(box):

從當前圖像返回矩形區域的副本,box是一個4元祖,定義從左、上、右、下的像素坐標

#剪切圖像
box=(100,100,400,400) #定義了圖像的坐標位置,從左、上、右、下
im=Image.open('images/22.jpg','r')
print(im.size)
region=im.crop(box)  #它會從左上角開始,同時向下和向右移動100像素的位置開始截取400-100的像素寬高,也就是300x300的圖像
print(region.size)
region.save('images/300x300.jpg')

im.filter(filter):

返回由給定過濾器過濾的圖像的副本

im.getbands():

返回包含每個band的名稱的元組。例如, RGB圖像上的getband返回(“R”,“G”,“B”)

from PIL import Image
im=Image.open('1.jpg')
im1=Image.new('L',(1080,1050),100)
assert isinstance(im,Image.Image)
print(im1.getbands())
print(im.getbands())
im1.show()

#
('L',)
('R', 'G', 'B')

im.getbbox():

計算圖像中非零區域的邊界框

from PIL import Image
im=Image.open('1.jpg')
im1=Image.new('L',(1080,1050),100)
assert isinstance(im,Image.Image)
print(im.getbbox())
print(im1.getbbox())

#
(0, 0, 1229, 768)
(0, 0, 1080, 1050)

im.getcolors(maxcolors):

返回元祖的末排序列表

from PIL import Image
im=Image.open('1.jpg')
im1=Image.new('L',(1080,1050),100)
assert isinstance(im,Image.Image)
print(im.getcolors())
print(im1.getcolors()) #返回計數和顏色的元組

#
None
[(1134000, 100)]

im.getdata():

將圖像的內容作為包含像素值的序列對象返回

im.getextrema():

返回包含圖像最小值和最大值的2元組,僅適用於單波段圖像

im.getpixel(xy):

返回給定位置的像素。如果圖像是多層圖像,則此方法返回元組

from PIL import Image

im=Image.open('1.jpg')
im1=Image.new('L',(1080,1050),100)
assert isinstance(im,Image.Image)
print(list(im.getdata()))  #返回圖像的像素值列表
print(im.getextrema()) #返回圖像的最小和最大值元組
print(im.getpixel((15,15))) #返回給定位置的像素元組

#
14, 233), (205, 210, 229), (209, 212, 229)......
((0, 255), (0, 255), (0, 255))
(10, 59, 76)

im.load():

映像分配存儲並從文件加載它

im.point(table):

返回圖像的副本,其中每個像素已通過給定的查找表進行映射

from PIL import Image

im=Image.open('1.jpg')
assert isinstance(im,Image.Image)
#調整灰色圖像的對比度
im_point=im.convert('L').point(lambda i:i < 80 and 255)
im_point.show()
source=im.split()
#三通道分別處理對比度
mask_r=source[0].point(lambda i:i < 80 and 255)
mask_g=source[1].point(lambda i:i < 80 and 255)
mask_b=source[2].point(lambda i:i < 80 and 255)
mask_r.show()
mask_g.show()
mask_b.show()

im.resize(size,filter=None):

返回圖像的已調整大小的副本

from PIL import Image

#filter為濾波器:將多個輸入像素映射為一個輸出像素的幾何操作,PIL提供的采樣濾波器:
#NEAREST:最近濾波。從輸入圖像中選取最近的像素作為輸出像素。它忽略了所有其他的像素
#BILINEAR:雙線性濾波。在輸入圖像的2x2矩陣上進行線性插值,,做下采樣時該濾波器使用了固定輸入模板
#BICUBIC:雙立方濾波。在輸入圖像的4x4矩陣上進行立方插值,做下采樣時該濾波器使用了固定輸入模板
#ANTIALIAS:平滑濾波,對所有可以影響輸出像素的輸入像素進行高質量的重采樣濾波,以計算輸出像素值,這個濾波器只用於改變尺寸和縮略圖方法
#ANTIALIAS濾波器是下采樣,將大圖轉換為小圖或左縮略圖時唯一正確的濾波器,BILIEAR和BICUBIC濾波器使用固定的輸入模板,用於固定比例的幾何變換和上采樣是最好的

im=Image.open('1.jpg') #type:Image.Image
print(im.size)
img1=im.resize((1024,768),Image.BILINEAR)
img2=im.resize((1024,768),Image.BICUBIC)
img3=im.resize((1024,768),Image.ANTIALIAS)
img4=im.resize((1024,768),Image.NEAREST)
im.show()
img1.show()
img2.show()
img3.show()
img4.show()

im.rotate(angle):

返回圍繞其中心逆時針旋轉給定度數的圖像副本

from PIL import Image

image1=Image.open('1.jpg')
assert isinstance(image1,Image.Image) #pycharm定義實例類
img1=image1.resize((1680,1050)) #返回跳轉圖像尺寸的副本
img1.show()
img2=img1.rotate(90)   #逆時針旋轉圖像90度
img2.show()

im.save(outfile,format,options):

將圖像保存在給定的文件名下

im.seek(frame):

尋找序列文件中的給定幀

im.show():

顯示圖像

im.split():

返回圖像中各個圖像帶的元組

from PIL import Image
im=Image.open('1.jpg')
assert isinstance(im,Image.Image)
source=im.split()  #分隔RGB三通道顏色的副本
print(source)
source[0].show() 
source[1].show()
source[2].show()

#
(<PIL.Image.Image image mode=L size=1229x768 at 0xE8D3ADACC0>, <PIL.Image.Image image mode=L size=1229x768 at 0xE8D3AE9048>, <PIL.Image.Image image mode=L size=1229x768 at 0xE8D3AE9080>)

im.tell():

返回當前幀編號

im.thumbnail(size):

修改圖像以包含其自身的縮略圖版本

from PIL import Image

size=(128,128)
im=Image.open('images/31.gif','r')
print(im.size)
im.thumbnail(size)   #它會根據圖像的寬高比例縮小,以最大的值為標准
im.save('images/55.gif','GIF')
print(im.size,im.format)


#
(275, 434)
(81, 128) GIF

im.paste(image,box):

將另一張圖像粘貼到此圖像中

im.transpose(method):

返回圖像的翻轉或旋轉副本

from PIL import Image

#剪切和粘貼圖像
box=(100,100,400,400) #定義了圖像的坐標位置,從左、上、右、下
im=Image.open('images/162.jpg')
print(im.size)
region=im.crop(box)  #它會從左上角開始,同時向下和向右移動100像素的位置開始截取400-100的像素寬高,也就是300x300的圖像
print(region.size)
#region.save('images/500x500.jpg')

region_tran180=region.transpose(Image.ROTATE_180) #旋轉圖像180度

im.paste(region_tran180,box)  #按照像素比例粘貼回去

im.verify():

嘗試確定文件是否損壞,而不實際解碼圖像數據

im.format:

源文件的文件格式

im.mode:

圖像模式典型值為“1”,“L”,“RGB”或“CMYK”

im.size:

圖像大小,以像素為單位。大小以2元組(寬度,高度)給出

im.palette:

調色板表

im.info:

保存與圖像相關的數據的字典

#!/usr/bin/env python
#coding:utf-8
from PIL import Image

#從文件中加載圖像
im=Image.open("images/22.jpg")
print(im.format)   #顯示圖像類型
print(im.size)   #顯示圖像的寬度和高度,像素為單位的2元祖
print(im.mode)  #顯示圖像屬性中波段的數量和名稱,以及像素類型和深度,常見模式有灰色圖像"L"表示亮度,真彩色圖像的"RGB"和印刷圖像模式“CMYK”
im.show()  #調用程序顯示圖像

#
JPEG
(1024, 768)
RGB

ImageChops模塊

ImageChops模塊包含多個算術圖像的操作,稱為通道操作,它們可以實現,特殊效果,圖像合成,算法繪畫等

它的功能大多數通道操作都是采用一個或兩個圖像參數比較來返回一個新圖像,下面只列出一些常用的方法:

IC.lighter(image1,image2):

逐個像素地比較兩個圖像,並返回包含較亮值的新圖像

from PIL import Image
from PIL import ImageChops
im1=Image.open('1.jpg')
im2=Image.open('2.jpg')

IC_image=ImageChops.lighter(im1,im2)
IC_image.show()

IC.darker(image1,image2):

逐個像素地比較兩個圖像,並返回包含較暗值的新圖像

IC.difference(image1,image2):

返回兩個圖像之間差異的絕對值

IC.multiply(image1,image2):

將兩個圖像疊加在一起。如果將圖像與純黑色圖像相乘,則結果為黑色。如果乘以純白圖像,則圖像不受影響

IC.screen(image1,image2):

將兩個倒置的圖像疊加在一起

IC.add(image1,image2,scle,offset):

添加兩個圖像,按比例划分結果並添加偏移量

IC.subtract(image1,image2,scale,offset):

減去兩個圖像,按比例划分結果並添加偏移量

ImageColor模塊

ImageColor模塊用來實現RGB顏色表轉換,它支持是顏色格式包括:

  • 十六進制顏色說明符,例如,#ff0000指定純紅色
  • RGB函數,以“rgb(紅色,綠色,藍色)”給出,其中顏色值是0到255范圍內的整數,如,“rgb(255,0,0)”和“rgb(100%,0%,0%)
  • 常見的HTML顏色名稱,例如,“red”指定純紅色

getrgb(color):將顏色字符串轉換為RGB元組

from PIL import ImageColor
IC_image=ImageColor.getrgb('red')
print(IC_image)

# (255, 0, 0)

getcolor(color,mode):與getrgb相同,但如果模式不是顏色或調色板圖像,則將RGB值轉換為灰度值

總結

PIL庫可以完成圖像歸檔和圖像處理兩方面功能需求:

(1)圖像歸檔:對圖像進行批處理、生成圖像預覽、圖像格式轉換等;

(2)圖像處理:圖像基本處理、像素處理、顏色處理等。

img

img

img

img

img

img

img


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM