Как изменить размер изображения с OpenCV2.0 и Python2.6
Я хочу использовать OpenCV2.0 и Python2.6 для отображения изображений с измененным размером. Я использовал и принял пример по адресу http://opencv.willowgarage.com/documentation/python/cookbook.html но, к сожалению, этот код предназначен для OpenCV2.1 и, похоже, не работает на 2.0. Вот мой код:
import os, glob
import cv
ulpath = "exampleshq/"
for infile in glob.glob( os.path.join(ulpath, "*.jpg") ):
im = cv.LoadImage(infile)
thumbnail = cv.CreateMat(im.rows/10, im.cols/10, cv.CV_8UC3)
cv.Resize(im, thumbnail)
cv.NamedWindow(infile)
cv.ShowImage(infile, thumbnail)
cv.WaitKey(0)
cv.DestroyWindow(name)
Так как я не могу использовать
cv.LoadImageM
я использовал
cv.LoadImage
вместо этого, что не было проблемой в других приложениях. Тем не менее, у cv.iplimage нет строк атрибутов, столбцов или размера. Может кто-нибудь дать мне подсказку, как решить эту проблему? Благодарю.
4 ответа
Если вы хотите использовать CV2, вам нужно использовать resize
функция.
Например, это изменит размеры обеих осей наполовину:
small = cv2.resize(image, (0,0), fx=0.5, fy=0.5)
и это изменит размер изображения, чтобы иметь 100 столбцов (ширина) и 50 строк (высота):
resized_image = cv2.resize(image, (100, 50))
Другой вариант заключается в использовании scipy
модуль, используя:
small = scipy.misc.imresize(image, 0.5)
Очевидно, есть больше опций, которые вы можете прочитать в документации этих функций ( cv2.resize, scipy.misc.imresize).
Обновить:
Согласно документации SciPy:
imresize
устарела в SciPy 1.0.0 и будет удалена в 1.2.0.
использованиеskimage.transform.resize
вместо.
Обратите внимание, что если вы хотите изменить размер, вы можете захотеть skimage.transform.rescale
,
Пример удвоения размера изображения
Есть два способа изменить размер изображения. Новый размер может быть указан:
Вручную;
height, width = src.shape[:2]
dst = cv2.resize(src, (2*width, 2*height), interpolation = cv2.INTER_CUBIC)
По коэффициенту масштабирования.
dst = cv2.resize(src, None, fx = 2, fy = 2, interpolation = cv2.INTER_CUBIC)
где fx - коэффициент масштабирования по горизонтальной оси и fy по вертикальной оси.
Чтобы уменьшить изображение, оно обычно будет выглядеть лучше с интерполяцией INTER_AREA, тогда как для увеличения изображения это будет выглядеть лучше всего с INTER_CUBIC (медленно) или INTER_LINEAR (быстрее, но все еще выглядит хорошо).
Пример уменьшенного изображения для соответствия максимальной высоте / ширине (с сохранением соотношения сторон)
import cv2
img = cv2.imread('YOUR_PATH_TO_IMG')
height, width = img.shape[:2]
max_height = 300
max_width = 300
# only shrink if img is bigger than required
if max_height < height or max_width < width:
# get scaling factor
scaling_factor = max_height / float(height)
if max_width/float(width) < scaling_factor:
scaling_factor = max_width / float(width)
# resize image
img = cv2.resize(img, None, fx=scaling_factor, fy=scaling_factor, interpolation=cv2.INTER_AREA)
cv2.imshow("Shrinked image", img)
key = cv2.waitKey()
Использование вашего кода с cv2
import cv2 as cv
im = cv.imread(path)
height, width = im.shape[:2]
thumbnail = cv.resize(im, (width/10, height/10), interpolation = cv.INTER_AREA)
cv.imshow('exampleshq', thumbnail)
cv.waitKey(0)
cv.destroyAllWindows()
Вы можете использовать функцию GetSize для получения этой информации, cv.GetSize(im) вернет кортеж с шириной и высотой изображения. Вы также можете использовать im.depth и img.nChan для получения дополнительной информации.
И чтобы изменить размер изображения, я бы использовал немного другой процесс, с другим изображением вместо матрицы. Лучше попытаться работать с однотипными данными:
size = cv.GetSize(im)
thumbnail = cv.CreateImage( ( size[0] / 10, size[1] / 10), im.depth, im.nChannels)
cv.Resize(im, thumbnail)
Надеюсь это поможет;)
Julien
Вот функция для увеличения или уменьшения изображения на желаемую ширину или высоту при сохранении соотношения сторон.
# Resizes a image and maintains aspect ratio
def maintain_aspect_ratio_resize(image, width=None, height=None, inter=cv2.INTER_AREA):
# Grab the image size and initialize dimensions
dim = None
(h, w) = image.shape[:2]
# Return original image if no need to resize
if width is None and height is None:
return image
# We are resizing height if width is none
if width is None:
# Calculate the ratio of the height and construct the dimensions
r = height / float(h)
dim = (int(w * r), height)
# We are resizing width if height is none
else:
# Calculate the ratio of the width and construct the dimensions
r = width / float(w)
dim = (width, int(h * r))
# Return the resized image
return cv2.resize(image, dim, interpolation=inter)
Применение
import cv2
image = cv2.imread('1.png')
cv2.imshow('width_100', maintain_aspect_ratio_resize(image, width=100))
cv2.imshow('width_300', maintain_aspect_ratio_resize(image, width=300))
cv2.waitKey()
Используя этот пример изображения
Просто уменьшите масштаб до width=100
(слева) или до width=300
(верно)
def rescale_by_height(image, target_height, method=cv2.INTER_LANCZOS4):
"""Rescale `image` to `target_height` (preserving aspect ratio)."""
w = int(round(target_height * image.shape[1] / image.shape[0]))
return cv2.resize(image, (w, target_height), interpolation=method)
def rescale_by_width(image, target_width, method=cv2.INTER_LANCZOS4):
"""Rescale `image` to `target_width` (preserving aspect ratio)."""
h = int(round(target_width * image.shape[0] / image.shape[1]))
return cv2.resize(image, (target_width, h), interpolation=method)