0%

電腦視覺概要#1 ── 認識數位影像

在電腦系統中,資料皆以二進位數字(0或1)儲存,圖片檔也不例外。一張圖片中的各個位置,亮度、顏色都不盡相同,因此每個位置皆需儲存不同資訊,才能保留圖片的特徵。一種簡單的做法是將圖片切割為大量細小的正方形區域,每個區域包含獨立的顏色、亮度等性質。我們將一個正方形區域稱為一個像素(pixel)。而透過這種方式儲存的圖片資料,稱為數位影像

像素

像素的英文是pixel,由picture(圖片)和element(元素)兩個單字組合而成,代表圖片的元素。我們可以將像素理解為影像的最小單位,而一張完整的影像由大量的像素組成。一般而言,影像檔案通常是矩形,因此影像尺寸通常由寬度和高度表示。例如一張圖片的尺寸為1080x2400,代表其寬度為1080像素、高度為2400像素。在後續影像處理的章節中,我們也會從像素的角度分析影像,並操縱個別像素的性質。

實作:影像讀取與顯示

在這個小節中,我們將會透過Python程式語言與openCV函式庫,讀取圖片檔並開啟視窗顯示該圖片。同時,配合上文提到的影像尺寸概念,分析該圖片檔的寬度與高度。

openCV函式庫安裝

首先,確保已成功安裝Python(關於Python的安裝,可點選此連結)。接著開啟終端機,輸入指令

1
pip install opencv-python

即可安裝openCV函式庫。

影像輸入輸出

透過openCV,我們可以輕易進行影像讀取與儲存。在開始實驗前,需要先準備一張影像檔案(bmp, png或jpg影像皆可),此文章中使用的範例影像為lena.bmp(見下圖)。
lena.bmp

在影像檔所在的資料夾中,建立python檔案image_IO.py:

image_IO.py
1
2
3
4
5
6
7
8
9
10
11
12
import cv2                      # 引用openCV函式庫

# 1. 影像讀取
img = cv2.imread('lena.bmp') # 讀取影像lena.bmp,存放於變數img

# 2. 影像顯示
cv2.imshow('test', img) # 在視窗中顯示影像img,視窗名為test
cv2.waitKey(0) # 等待使用者輸入
cv2.destroyAllWindows() # 關閉所有視窗

# 3. 影像儲存
cv2.imwrite('output.bmp', img) #儲存影像img,檔名為output.bmp

以上程式碼為openCV最基礎的用法,在未來的教學文章中會持續使用。各位不妨實際操作一次,可以發現在執行程式後,會自動開啟一個視窗顯示影像,而使用者按下任意鍵可關閉該視窗。接著會以output.bmp為檔名儲存該影像,達成另存新檔的效果。

取得影像尺寸

我們可以透過type()函數取得變數img的型態。

1
2
3
4
import cv2

img = cv2.imread('lena.bmp') # 讀取影像lena.bmp,存放於變數img
print(type(img)) # 輸出img的型態名稱

執行此程式,得到輸出為

1
<class 'numpy.ndarray'>

可知img實際上為numpy陣列。引入numpy package後,可以用其內建的shape()函數得到img的維度資訊。

1
2
3
4
5
6
7
import cv2
import numpy as np # 引入numpy(用於陣列處理)

img = cv2.imread('lena.bmp') # 讀取影像lena.bmp,存放於變數img
print(np.shape(img)) # 印出img的維度資訊
height = img.shape[0] # 影像高度
width = img.shape[1] # 影像寬度

執行後可發現img的shape為(512, 512, 3),其中第一項為高度,第二項為寬度,第三項代表RGB共三種通道。在這個例子中,圖片的高度與寬度相同,因此不容易確認shape中哪一項代表高度、哪一項代表寬度。讀者可以嘗試使用長寬不相同的圖片檔進行實驗,相信你會得到結論。