Python – Storing a dataset of images into a 4D array and then displaying each image results in color distortion

Storing a dataset of images into a 4D array and then displaying each image results in color distortion… here is a solution to the problem.

Storing a dataset of images into a 4D array and then displaying each image results in color distortion

I’m trying to store a dataset of images into a 4D ndarray and then draw each image as follows:

i=0
for j in imagelist:
  imageall[i] = misc.imread(j) ##(36, 570, 760, 3)
  plt.imshow(imageall[i])
  plt.show()
  i=i+1

However, displaying an image from a 4D ndarray displays a bluish image, while simply reading the image and drawing it shows the normal color of the image.

I compared channel (in both cases by visual and computational means are exactly the same).

Can anyone explain the change in display image shading when reading a single image and reading to a 4D ndarray?

Result from showing single image

Result from showing the same image but from the 4D ndarray

Solution

Your image has the same channel value as you indicated in the question, so the difference in the results indicates that plt.imshow interprets your value differently. The way plt.imshow interprets images based on type is somewhat magical, so the most likely reason is that your original array was initialized with the wrong dtype.

Let’s say your pre-allocation is like

import numpy as np
imageall = np.empty((n_img,width,height,3))
# or imageall = np.zeros((n_img,width,height,3))

The resulting array will automatically have a double type, which is dtype=np.float64. When you change this array with each image, the input dtype=np.uint8 (returned from plt.imread) is converted to double, effectively doing

imageall[i] = misc.imread(j).astype(np.float64)

Therefore, channel values from 0 to 255 are stored as float and then misinterpreted by plt.imshow.

You just need to pre-allocate with the correct data type:

imageall = np.empty((n_img,width,height,3),dtype=np.uint8)

Related Problems and Solutions