【问题标题】:How to speedup caffe for sliding window object detection in a test image如何加快咖啡馆在测试图像中的滑动窗口对象检测
【发布时间】:2017-04-20 09:14:47
【问题描述】:

问题:

我已经训练了一个卷积神经网络 (CNN) 来确定/检测给定图像块中是否存在感兴趣的对象。

现在给定一张大图像,我试图通过将我的 CNN 模型应用于图像中每个像素周围的补丁,以滑动窗口方式定位图像中所有出现的对象。然而,这是非常缓慢的。

我的测试图像大小为 (512 x 512)。而且,对于我的 caffe 网络,测试批次大小为 1024,补丁大小为 (65 x 65 x 1)。

我尝试将我的 caffe 网络应用于一批补丁(大小 = test_batch_size),而不是一次应用一个补丁。即使那样它也很慢。

以下是我当前非常慢的解决方案。除了对我的测试图像进​​行下采样以加快速度之外,我将不胜感激任何其他建议。

当前非常慢的解决方案:

def detectObjects(net, input_file, output_file):

    # read input image
    inputImage = plt.imread(input_file)

    # get test_batch_size and patch_size used for cnn net
    test_batch_size = net.blobs['data'].data.shape[0]
    patch_size = net.blobs['data'].data.shape[2]

    # collect all patches    
    w = np.int(patch_size / 2)

    num_patches = (inputImage.shape[0] - patch_size) * \
                  (inputImage.shape[1] - patch_size)

    patches = np.zeros((patch_size, patch_size, num_patches))
    patch_indices = np.zeros((num_patches, 2), dtype='int64')

    count = 0

    for i in range(w + 1, inputImage.shape[0] - w):
        for j in range(w + 1, inputImage.shape[1] - w):

            # store patch center index
            patch_indices[count, :] = [i, j]

            # store patch
            patches[:, :, count] = \
                inputImage[(i - w):(i + w + 1), (j - w):(j + w + 1)]

            count += 1

    print "Extracted %s patches" % num_patches

    # Classify patches using cnn and write result to output image
    outputImage = np.zeros_like(inputImage)
    outputImageFlat = np.ravel(outputImage)

    pad_w = test_batch_size - num_patches % test_batch_size
    patches = np.pad(patches, ((0, 0), (0, 0), (0, pad_w)),
                     'constant')
    patch_indices = np.pad(patch_indices, ((0, pad_w), (0, 0)),
                           'constant')

    start_time = time.time()

    for i in range(0, num_patches, test_batch_size):

        # get current batch of patches
        cur_pind = patch_indices[i:i + test_batch_size, :]

        cur_patches = patches[:, :, i:i + test_batch_size]
        cur_patches = np.expand_dims(cur_patches, 0)
        cur_patches = np.rollaxis(cur_patches, 3)

        # apply cnn on current batch of images
        net.blobs['data'].data[...] = cur_patches

        output = net.forward()

        prob_obj = output['prob'][:, 1]

        if i + test_batch_size > num_patches:

            # remove padded part
            num_valid = num_patches - i
            prob_obj = prob_obj[0:num_valid]
            cur_pind = cur_pind[0:num_valid, :]

        # set output
        cur_pind_lin = np.ravel_multi_index((cur_pind[:, 0],
                                             cur_pind[:, 1]),
                                             outputImage.shape)

        outputImageFlat[cur_pind_lin] = prob_obj

    end_time = time.time()
    print 'Took %s seconds' % (end_time - start_time)

    # Save output
    skimage.io.imsave(output_file, outputImage * 255.0)

我希望有这些台词

    net.blobs['data'].data[...] = cur_patches
    output = net.forward()

caffe 将使用 GPU 对 cur_patches 中的所有补丁进行并行分类。想知道为什么它仍然很慢。

【问题讨论】:

  • 你用什么网?将其转换为卷积网络。
  • @Shai 我正在使用 CNN。我解决了这个问题。我使用的是 net_test.prototxt 而不是 net_deploy.prototxt,这会导致一些奇怪的行为。我在部署模式下调整了批量大小,批量大小为 1000,我可以在 9 秒内对 512 x 512 图像中的所有补丁(~200000)进行密集分类,我现在很满意。非常感谢您对生成 net_deploy.prototxt 的帮助。

标签: python deep-learning caffe conv-neural-network object-detection


【解决方案1】:

我认为Casting a Classifier into a Fully Convolutional Network of the "net surgery" tutorial 部分描述了您要查找的内容。
这个解决方案的基本意思是,可以将"InnerProduct" 层转换为等效 层,而不是转换层后跟"InnerProduct" 层进行分类,从而产生完全卷积 网络,可以处理任意大小的图像并根据输入大小输出预测。
迁移到完全卷积架构将显着减少您当前进行的冗余计算数量,并应显着加快您的流程。


另一个可能的加速方向是通过使用truncated SVD trick 的两个较低等级矩阵的乘积近似高维"InnerProduct" 层。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-10-31
    • 2017-01-11
    • 2021-12-18
    • 1970-01-01
    • 1970-01-01
    • 2015-08-29
    • 2020-04-02
    • 1970-01-01
    相关资源
    最近更新 更多