python代码执行逻辑_如何在Python中使用VIPS执行逻辑操作和逻辑索引?

本文介绍了如何将原本使用OpenCV实现的图像处理代码转换为使用VIPS库,特别是针对大型图像的逻辑操作和索引。通过VIPS的ifthenelse方法实现了逻辑索引,从而提高了处理速度。
摘要由CSDN通过智能技术生成

I've had following codes that use Python and OpenCV. Briefly, I have a stack of image taken at different focal depth. The codes pick out pixels at every (x,y) position that has the largest Laplacian of Guassian response among all focal depth(z), thus creating a focus-stacked image. Function get_fmap creates a 2d array where each pixel will contains the number of the focal plane having the largest log response. In the following codes, lines that are commented out are my current VIPS implementation. They don't look compatible within the function definition because it's only partial solution.

# from gi.repository import Vips

def get_log_kernel(siz, std):

x = y = np.linspace(-siz, siz, 2*siz+1)

x, y = np.meshgrid(x, y)

arg = -(x**2 + y**2) / (2*std**2)

h = np.exp(arg)

h[h < sys.float_info.epsilon * h.max()] = 0

h = h/h.sum() if h.sum() != 0 else h

h1 = h*(x**2 + y**2 - 2*std**2) / (std**4)

return h1 - h1.mean()

def get_fmap(img): # img is a 3-d numpy array.

log_response = np.zeros_like(img[:, :, 0], dtype='single')

fmap = np.zeros_like(img[:, :, 0], dtype='uint8')

log_kernel = get_log_kernel(11, 2)

# kernel = get_log_kernel(11, 2)

# kernel = [list(row) for row in kernel]

# kernel = Vips.Image.new_from_array(kernel)

# img = Vips.new_from_file("testimg.tif")

for ii in range(img.shape[2]):

# img_filtered = img.conv(kernel)

img_filtered = cv2.filter2D(img[:, :, ii].astype('single'), -1, log_kernel)

index = img_filtered > log_response

log_response[index] = img_filtered[index]

fmap[index] = ii

return fmap

and then fmap will be used to pick out pixels from different focal planes to create a focus-stacked image

This is done on an extremely large image, and I feel VIPS might do a better job than OpenCV on this. However, the official documentation provides rather scant information on its Python binding. From the information I can find on the internet, I'm only able to make image convolution work ( which, in my case, is an order of magnitude faster than OpenCV.). I'm wondering how to implement this in VIPS, especially these lines?

log_response = np.zeros_like(img[:, :, 0], dtype = 'single')

index = img_filtered > log_response

log_response[index] = im_filtered[index]

fmap[index] = ii

解决方案

After consulting the Python VIPS manual and some trial-and-error, I've come up with my own answer. My numpy and OpenCV implementation in question can be translated into VIPS like this:

import pyvips

img = []

for ii in range(num_z_levels):

img.append(pyvips.Image.new_from_file("testimg_z" + str(ii) + ".tif")

def get_fmap(img)

log_kernel = get_log_kernel(11,2) # get_log_kernel is my own function, which generates a 2-d numpy array.

log_kernel = [list(row) for row in log_kernel] # pyvips.Image.new_from_array takes 1-d list array.

log_kernel = pyvips.Image.new_from_array(log_kernel) # Turn the kernel into Vips array so it can be used by Vips.

log_response = img[0].conv(log_kernel)

for ii in range(len(img)):

img_filtered = img[ii+1].conv(log_kernel)

log_response = (img_filtered > log_response).ifthenelse(img_filtered, log_response)

fmap = (img_filtered > log_response).ifthenelse(ii+1, 0)

Logical indexing is achieved through ifthenelse method :

result_img = (test_condition).ifthenelse(value_if_true, value_if_false)

The syntax is rather flexible. The test condition can be a comparison between two images of the same size or between an image and a value, e.g. img1 > img2 or img > 5. Like wise, value_if_true can be a single value or a Vips image.

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值