Numpy:Python科学计算工具包,其中包含了大量有用的思想,比如数组对象(用来表示向量、矩阵、图像等)以及线性代数函数。数组对象可以帮助实现数组中的重要操作,比如矩阵乘积、转置、解方程系统、向量乘积和归一化,这为图像变形、对变换进行建模、图像分类、图像聚类等提供了基础。
文章目录
- 图像数组表示
- 图像数组表示
- 访问数组中的元素
- 灰度变换
- 图像缩放
- 直方图均衡化
- np.zeros()函数
- image.shape
- cv2.imread()
- cv2.copyMakeBorder()函数
图像数组表示
载入图象时,调用array()方法将图像转换成Numpy的数组对象,数组对象是多维的,可以用来表示向量、矩阵和图像。数组中的所有元素必须具有相同的数据类型,除非创建数据对象时指定数据类型,否则数据类型会按照数据的类型自动确定。
im = array(Image.open('empire.jpg'))
print im.shape, im.dtype
im = array(Image.open('empire.jpg').convert('L'), 'f')
print im.shape, im.dtype
以下为控制台输出结果:
(800, 569, 3) uint8 # 第一个元组表示图像数组的大小(行、列、颜色通道)uint8:数组元素的数据类型,图像通常被编码成无符号八位整数(uint8) (800, 569) float32
说明:第一种情况,载入图像并将其转换到数组中,数组的数据类型为“uint8”,第二种情况,对图像进行灰度化处理,并在创建数组时使用额外的参数“f”,将数据类型转换为浮点型。
灰度图像没有颜色信息,在形状数组中,只有两个数值。
value = im[i, j, k] # 访问 位于坐标i, j, 以及颜色通道K的像素值 # 数组切片方式访问多个数组元素 # 切片方式返回的是以指定间隔下标访问该数组的元素值 im[i, :] = im[j, :] # 将第j行的所有数值赋值给第i行 im[:, i] = 100 # 将第i列的所有数值设为100 im[:100, :50].sum() # 计算前100行、前50列所有数值的和 im[i].mean() # 第i行所有数值的平均值 im[:, -1] # 最后一列 im[-2, :] # 倒数第二行 # 如果仅使用一个下标, 则该下标为行下标灰度变换
图像读入Numpy数组对象后,可以对其执行任意数学操作。
例如灰度变换
from PIL import Image
from numpy import *
im = array(Image.open('empire.jpg').convert('L'))
im2 = 255 - im # 对图像进行反相处理
im3 = (100.0/255)*im + 100 # 对图像像素值变换到100...200区间
im4 = 255.0 * (im/255.0)**2 # 对图像像素值求平方后得到的图像
# 即对图像进行二次函数变换, 使较暗的像素值变得更小
array()变换的相反操作可以使用PIL的fromarray()函数完成
pil_im = Image.fromarray(im)
在创建PIL图像之前需要将数据类型从其他数据类型转换为(uint8)转换回来。
图像缩放对图像进行缩放处理没有现成简单的方法,Numpy的数组对象是我们处理图像和数据的主要工具。
可以使用PIL对图像对象转换的操作,写一个用于图像缩放的函数
def imresize(im, sz):
"""使用PIL对象重新定义图像数组的大小"""
pil_im = Image.fromarray(uint8(im))
return array(pil_im.resize(sz))
直方图均衡化
直方图均衡化:将一幅图像的灰度直方图变平,使变换后的图像中每个灰度值的分布概率都相同。
在对图像做进一步处理之前,直方图均衡化通常是对图像灰度值进行归一化的一个非常好的方法,并且可以增强图像的对比度。
在 该情况下,直方图均衡化的变换图像是图像中像素值的累积分布函数(cdf)即 将像素值的范围映射到目标范围的归一化操作。
def histeq(im, nbr_bins = 256):
"""对一幅灰度图像进行直方图均衡化"""
# 计算图像的直方图
imhist, bins = histogram(im.flatten(), nbr_bins, normed = True)
cdf = imhist.cumsum() # 累积分布函数
cdf = 255*cdf / cdf[-1] # 归一化到 0...1 范围
# 使用累积分布函数的线性插值, 计算新的像素值
im2 = interp(im.flatten(), bins[: -1], cdf)
return im2.reshape(im.shape),cdf
np.zeros()函数
返回来一个给定形状和类型的用0填充的数组;
zeros(shape, dtype=float, order=‘C’)
shape:形状
dtype:数据类型,可选参数,默认numpy.float64
order:可选参数,c代表与c语言类似,行优先;F代表列优先
import numpy as np print(np.zeros((2,5)))
输出:
2行5列的矩阵
print(np.zeros((2,5),dtype= np.int))
输出
图像的数据结构
当用img = cv2.imread(‘pic.png’)的时候:
用img.shape返回的是: (height, width, channel)
height: 图片的垂直尺寸
width: 图片的水平尺寸
channel: 图片的通道数
Mat cv::imread(const string& filename,int flags=IMREAD_COLOR);
cv2.copyMakeBorder()函数IMREAD_UNCHANGED = -1, //返回包含alpha通道的加载图像
IMREAD_GRAYSCALE = 0, //返回一个灰度图像
IMREAD_COLOR = 1, //返回一个BGR通道的图像
IMREAD_ANYDEPTH = 2, //当输入具有相应的深度时返回16位/ 32位图像,否则将其转换为8位。.
IMREAD_ANYCOLOR = 4, //则以任何可能的颜色格式读取图像。
IMREAD_LOAD_GDAL = 8, //使用GDAL的驱动加载图像。
IMREAD_REDUCED_GRAYSCALE_2 = 16, //将图像转换为单通道灰度图像,图像大小减少1/2。
IMREAD_REDUCED_COLOR_2 = 17, //转换图像的3通道BGR彩色图像和图像的大小减少1/2。
IMREAD_REDUCED_GRAYSCALE_4 = 32, //将图像转换为单通道灰度图像,图像大小减少1/4。
IMREAD_REDUCED_COLOR_4 = 33, //转换图像的3通道BGR彩色图像和图像的大小减少1/4。
IMREAD_REDUCED_GRAYSCALE_8 = 64, //将图像转换为单通道灰度图像,图像大小减少1/8。
IMREAD_REDUCED_COLOR_8 = 65, //转换图像的3通道BGR色彩图像和图像大小减少1/8。
IMREAD_IGNORE_ORIENTATION = 128 //不旋转图像根据EXIF的定位标志。
copyMakeBorder(src, top, bottom, left, right, borderType[, dst[, value]])
src : 输入的图片 top, bottom, left, right :相应方向上的边框宽度
borderType:定义要添加边框的类型,它可以是以下的一种:
cv2.BORDER_CONSTANT:添加的边界框像素值为常数(需要额外再给定一个参数)
cv2.BORDER_REFLECT:添加的边框像素将是边界元素的镜面反射,类似于gfedcb|abcdefgh|gfedcba
cv2.BORDER_REFLECT_101 or cv2.BORDER_DEFAULT:和上面类似,但是有一些细微的不同,类似于gfedcb|abcdefgh|gfedcba
cv2.BORDER_REPLICATE:使用最边界的像素值代替,类似于aaaaaa|abcdefgh|hhhhhhh
cv2.BORDER_WRAP:不知道怎么解释,直接看吧, cdefgh|abcdefgh|abcdefg
value:如果borderType为cv2.BORDER_CONSTANT时需要填充的常数值。



