Бикубическая интерполяция для масштабирования изображения
Я пытаюсь реализовать очень простой би-кубический алгоритм, чтобы использовать его для масштабирования изображения. Я использовал другие вопросы о переполнении стека и попытался просто перевести код на Python.
Он работает правильно без каких-либо ошибок, я пару раз проверял математику, но не могу найти причину такого рода проблем, кажется, что все должно работать без сбоев, но в результате я получаю это:
Любая помощь приветствуется.
Вот источник:
def getBicPixelChannel(img,x,y,channel):
if x < img.shape[1] & y < img.shape[0]:
return img[y,x,channel]
return 0
def Bicubic(img, rate):
new_w = int(math.ceil(float(img.shape[1]) * rate))
new_h = int(math.ceil(float(img.shape[0]) * rate))
new_img = np.zeros((new_w, new_h, 3))
x_rate = float(img.shape[1]) / new_img.shape[1]
y_rate = float(img.shape[0]) / new_img.shape[0]
C = np.zeros(5)
for hi in range(new_img.shape[0]):
for wi in range(new_img.shape[1]):
x_int = int(wi * x_rate)
y_int = int(hi * y_rate)
dx = x_rate * wi - x_int
dy = y_rate * hi - y_int
for channel in range(new_img.shape[2]):
for jj in range(0,4):
o_y = y_int - 1 + jj
a0 = getBicPixelChannel(img,x_int,o_y, channel)
d0 = getBicPixelChannel(img,x_int - 1,o_y, channel) - a0
d2 = getBicPixelChannel(img,x_int + 1,o_y, channel) - a0
d3 = getBicPixelChannel(img,x_int + 2,o_y, channel) - a0
a1 = -1./3 * d0 + d2 - 1./6 * d3
a2 = 1./2 * d0 + 1./2 * d2
a3 = -1./6 * d0 - 1./2 * d2 + 1./6 * d3
C[jj] = a0 + a1 * dx + a2 * dx * dx + a3 * dx * dx * dx
d0 = C[0] - C[1]
d2 = C[2] - C[1]
d3 = C[3] - C[1]
a0 = C[1]
a1 = -1. / 3 * d0 + d2 - 1. / 6 * d3
a2 = 1. / 2 * d0 + 1. / 2 * d2
a3 = -1. / 6 * d0 - 1. / 2 * d2 + 1. / 6 * d3
new_img[hi, wi, channel] = a0 + a1 * dy + a2 * dy * dy + a3 * dy * dy * dy
return new_img
2 ответа
Я думаю, что ваша проблема в этой строке кода:
if x < img.shape[1] & y < img.shape[0]:
Из того, что я собираю, &
является побитовым оператором AND в Python и имеет более высокий приоритет, чем <
, Итак, что вы вычисляете это:
if x < ( img.shape[1] & y ) < img.shape[0]:
(что бы это ни значило...)
Вместо этого попробуйте это:
if (x < img.shape[1]) and (y < img.shape[0]):
and
является логическим оператором И Python.
Я также думаю, что необходимо еще одно изменение. (Иначе вы получите ошибку, если входное изображение имеет форму прямоугольника, а не квадрата)
new_img = np.zeros((new_w, new_h, 3))
здесь размеры указаны как (ширина, высота, канал), что означает (столбец, строка, канал) и неверно. Но на самом деле так должно быть:
new_img = np.zeros((new_h, new_w, 3))
Спасибо :)