簡體   English   中英

如何將 RGB 圖像轉換為 numpy 數組?

[英]how to convert an RGB image to numpy array?

我有一個 RGB 圖像。 我想將它轉換為 numpy 數組。 我做了以下

im = cv.LoadImage("abc.tiff")
a = numpy.asarray(im)

它創建一個沒有形狀的數組。 我假設它是一個 iplimage object。

您可以使用較新的 OpenCV python 接口(如果我沒記錯的話,它從 OpenCV 2.2 開始可用)。 它本身使用 numpy 數組:

import cv2
im = cv2.imread("abc.tiff",mode='RGB')
print type(im)

結果:

<type 'numpy.ndarray'>

PIL(Python 成像庫)和 Numpy 可以很好地協同工作。

我使用以下功能。

from PIL import Image
import numpy as np

def load_image( infilename ) :
    img = Image.open( infilename )
    img.load()
    data = np.asarray( img, dtype="int32" )
    return data

def save_image( npdata, outfilename ) :
    img = Image.fromarray( np.asarray( np.clip(npdata,0,255), dtype="uint8"), "L" )
    img.save( outfilename )

'Image.fromarray' 有點難看,因為我將傳入的數據剪輯為 [0,255],轉換為字節,然后創建一個灰度圖像。 我主要工作在灰色。

RGB 圖像類似於:

 outimg = Image.fromarray( ycc_uint8, "RGB" )
 outimg.save( "ycc.tif" )

您也可以為此使用matplotlib

from matplotlib.image import imread

img = imread('abc.tiff')
print(type(img))

輸出: <class 'numpy.ndarray'>

截至今天,您最好的選擇是使用:

img = cv2.imread(image_path)   # reads an image in the BGR format
img = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)   # BGR -> RGB

你會看到img將是一個 numpy 類型的數組:

<class 'numpy.ndarray'>

遲到的答案,但與其他替代方案imageio ,我更喜歡imageio模塊

import imageio
im = imageio.imread('abc.tiff')

cv2.imread()類似,它默認生成一個 numpy 數組,但采用 RGB 形式。

您需要使用 cv.LoadImageM 而不是 cv.LoadImage:

In [1]: import cv
In [2]: import numpy as np
In [3]: x = cv.LoadImageM('im.tif')
In [4]: im = np.asarray(x)
In [5]: im.shape
Out[5]: (487, 650, 3)

當使用 David Poole 的答案時,我收到一個帶有灰度 PNG 和其他文件的 SystemError。 我的解決辦法是:

import numpy as np
from PIL import Image

img = Image.open( filename )
try:
    data = np.asarray( img, dtype='uint8' )
except SystemError:
    data = np.asarray( img.getdata(), dtype='uint8' )

實際上 img.getdata() 可用於所有文件,但速度較慢,因此我僅在其他方法失敗時才使用它。

您可以通過使用Image from PIL numpyImage from PIL輕松獲取 rgb 圖像的 numpy 數組

import numpy as np
from PIL import Image
import matplotlib.pyplot as plt

im = Image.open('*image_name*') #These two lines
im_arr = np.array(im) #are all you need
plt.imshow(im_arr) #Just to verify that image array has been constructed properly

使用以下語法加載圖像:-

from keras.preprocessing import image

X_test=image.load_img('four.png',target_size=(28,28),color_mode="grayscale"); #loading image and then convert it into grayscale and with it's target size 
X_test=image.img_to_array(X_test); #convert image into array

OpenCV 圖像格式支持 numpy 數組接口。 可以使輔助函數支持灰度或彩色圖像。 這意味着可以使用 numpy 切片方便地完成 BGR -> RGB 轉換,而不是圖像數據的完整副本。

注意:這是一個跨步技巧,因此修改輸出數組也會更改 OpenCV 圖像數據。 如果你想要一個副本,在數組上使用.copy()方法!

import numpy as np

def img_as_array(im):
    """OpenCV's native format to a numpy array view"""
    w, h, n = im.width, im.height, im.channels
    modes = {1: "L", 3: "RGB", 4: "RGBA"}
    if n not in modes:
        raise Exception('unsupported number of channels: {0}'.format(n))
    out = np.asarray(im)
    if n != 1:
        out = out[:, :, ::-1]  # BGR -> RGB conversion
    return out

我也采用了 imageio,但我發現以下機器對預處理和后處理很有用:

import imageio
import numpy as np

def imload(*a, **k):
    i = imageio.imread(*a, **k)
    i = i.transpose((1, 0, 2))  # x and y are mixed up for some reason...
    i = np.flip(i, 1)  # make coordinate system right-handed!!!!!!
    return i/255


def imsave(i, url, *a, **k):
    # Original order of arguments was counterintuitive. It should
    # read verbally "Save the image to the URL" — not "Save to the
    # URL the image."

    i = np.flip(i, 1)
    i = i.transpose((1, 0, 2))
    i *= 255

    i = i.round()
    i = np.maximum(i, 0)
    i = np.minimum(i, 255)

    i = np.asarray(i, dtype=np.uint8)

    imageio.imwrite(url, i, *a, **k)

理由是我使用 numpy 進行圖像處理,而不僅僅是圖像顯示。 為此,uint8s 很笨拙,因此我將其轉換為 0 到 1 之間的浮點值。

保存圖像時,我注意到我必須自己刪除超出范圍的值,否則我最終會得到一個非常灰色的輸出。 (灰色輸出是 imageio 將整個范圍(在 [0, 256)之外壓縮到范圍內的值的結果。)

還有其他一些奇怪的事情,我在評論中提到過。

使用 Keras:

from keras.preprocessing import image
  
img = image.load_img('path_to_image', target_size=(300, 300))
x = image.img_to_array(img)
x = np.expand_dims(x, axis=0)
images = np.vstack([x])

我們可以使用以下function的open CV2來轉換BGR 2 RGB格式。

RBG_Image = cv2.cvtColor(Image, cv.COLOR_BGR2RGB)

嘗試對將圖像加載到 numpy 數組的選項進行計時,它們非常相似。 為了簡單和速度,去plt.imread

def time_this(function, times=100):
    cum_time = 0
    for t in range(times):
        st = time.time()
        function()
        cum_time += time.time() - st
    return cum_time / times

import matplotlib.pyplot as plt
def load_img_matplotlib(img_path):
    return plt.imread(img_path)

import cv2
def load_img_cv2(img_path):
    return cv2.cvtColor(cv2.imread(img_path), cv2.COLOR_BGR2RGB)

from PIL import Image
import numpy as np
def load_img_pil(img_path):
    img = Image.open(img_path)
    img.load()
    return np.asarray( img, dtype="int32" )

if __name__=='__main__':
    img_path = 'your_image_path'
    for load_fn in [load_img_pil, load_img_cv2, load_img_matplotlib]:
        print('-'*20)
        print(time_this(lambda: load_fn(img_path)), 10000)

結果:

--------------------
0.0065201687812805175 10000  PIL, as in [the second answer][1]https://stackoverflow.com/a/7769424/16083419)
--------------------
0.0053211402893066405 10000  CV2
--------------------
0.005320906639099121 10000  matplotlib

你可以試試下面的方法。 這是文檔的鏈接。

tf.keras.preprocessing.image.img_to_array(img, data_format=None, dtype=None)
from PIL import Image
img_data = np.random.random(size=(100, 100, 3))
img = tf.keras.preprocessing.image.array_to_img(img_data)
array = tf.keras.preprocessing.image.img_to_array(img)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM