Exibir imagem em escala de cinza usando matplotlib

231

Estou tentando exibir uma imagem em escala de cinza usando matplotlib.pyplot.imshow () . Meu problema é que a imagem em escala de cinza é exibida como um mapa de cores. Preciso da escala de cinza porque quero desenhar em cima da imagem com cores.

Eu li na imagem e converto para escala de cinza usando Image.open (). Convert ("L") do PIL

image = Image.open(file).convert("L")

Em seguida, converto a imagem em uma matriz, para que eu possa processar facilmente algumas imagens usando

matrix = scipy.misc.fromimage(image, 0)

No entanto, quando eu faço

figure()  
matplotlib.pyplot.imshow(matrix)  
show()

exibe a imagem usando um mapa de cores (ou seja, não é em escala de cinza).

O que eu estou fazendo errado aqui?

Ryan
fonte

Respostas:

368

O código a seguir carrega uma imagem de um arquivo image.pnge a exibe em escala de cinza.

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

fname = 'image.png'
image = Image.open(fname).convert("L")
arr = np.asarray(image)
plt.imshow(arr, cmap='gray', vmin=0, vmax=255)
plt.show()

Se você deseja exibir a escala de cinza inversa, mude o cmap para cmap='gray_r'.

unutbu
fonte
4
@ jay: Por esta sequência de documentos , "Observe que qualquer mapa de cores listado aqui pode ser revertido anexando _r".
unutbu
31
Aviso matplotlib ajuste a intensidade da escala de pixels se você não quiser usar:plt.imshow(im_gray,cmap='gray', vmin = 0, vmax = 255)
themadmax
17

import matplotlib.pyplot as plt

Você também pode executar uma vez no seu código

plt.gray()

Isso mostrará as imagens em escala de cinza como padrão

im = array(Image.open('I_am_batman.jpg').convert('L'))
plt.imshow(im)
plt.show()
Eliel Van Hojman
fonte
Para qual biblioteca você está usando gray()ou grey()?
SherylHohman
@ SherylHohman, é gray... cinza é a ortografia americana padrão e cinza é a ortografia britânica da mesma cor.
Cloud Cho
12

Eu usaria o método get_cmap. Ex.:

import matplotlib.pyplot as plt

plt.imshow(matrix, cmap=plt.get_cmap('gray'))
Al Conrad
fonte
11

A resposta do @ unutbu está bem próxima da resposta certa.

Por padrão, o plt.imshow () tentará dimensionar os dados da matriz (MxN) para 0,0 ~ 1,0. E então mapeie para 0 ~ 255. Para imagens mais naturais, tudo bem, você não verá uma diferença. Mas se você tiver um intervalo estreito de imagem com valor de pixel, diga que o pixel mínimo é 156 e o ​​pixel máximo é 234. A imagem cinza parecerá totalmente errada. A maneira correta de mostrar uma imagem em cinza é

from matplotlib.colors import NoNorm
...
plt.imshow(img,cmap='gray',norm=NoNorm())
...

Vamos ver um exemplo:

esta é a imagem original : original

isso está usando a configuração de norma padrão, que é Nenhuma: foto errada

isso está usando a configuração NoNorm, que é NoNorm (): foto direita

Stanley
fonte
9

tente isto:

import pylab
from scipy import misc

pylab.imshow(misc.lena(),cmap=pylab.gray())
pylab.show()
baco
fonte
não existe pylab.grey(), talvez tenha sido removido?
Lyndon White
4

Não use interpolação e defina para cinza.

import matplotlib.pyplot as plt
plt.imshow(img[:,:,1], cmap='gray',interpolation='none')
user3452134
fonte