1

我正在尝试使用 - LP Wong,HT Ewe 中描述的方法从胸部 X 射线图像中提取肺部区域。“使用胸部 X 射线图像进行肺癌检测的研究”。2005 年第三届 APT 远程医疗研讨会,2005 年 1 月 27 日至 28 日,马来西亚吉隆坡。第 210-214 页。我想在 Python 中复制的代码在这里 - http://www.mathworks.com/matlabcentral/mlc-downloads/downloads/submissions/12543/versions/1/previews/EulerMinMax.m/index.html

在翻译代码时,我遇到了以下问题:

  • 在 Python 中使用 OpenCV 计算图像的欧拉数 - 我尝试在 OpenCV 中使用“findContours”方法来实现这一点,但没有得到令人满意的结果。

我在下面附上了我的代码。我将非常感谢您对此发表任何评论。

import cv2
import numpy as np
import matplotlib.pyplot as plt

img = cv2.imread('chest.jpg',cv2.CV_LOAD_IMAGE_GRAYSCALE)
a = cv2.equalizeHist(img)
b = 255
arr_b = [i for i in range(b)]
trans_thresh = [float(i)/float(b) for i in arr_b]
result4_trans1 = []

def euler_number(image):
    contours, hierarchy = cv2.findContours(a,cv2.RETR_CCOMP, cv2.CHAIN_APPROX_SIMPLE)
    objects = len(contours)
    holes = 0
    for h in hierarchy[0]:
        if h[2] == -1:
            holes += 1
    eulerNumber = objects - holes
    return eulerNumber

def convert_to_binary_image(image, threshold, maxVal):
    ret, thresh = cv2.threshold(image, threshold, maxVal, cv2.THRESH_BINARY | cv2.THRESH_OTSU)
    return thresh


for j in range(b):
    value_trans1 = trans_thresh[j]
    binary_image = convert_to_binary_image(a, value_trans1, b)
    result4_trans1.append(euler_number(binary_image))

max_result4_trans1 = max(result4_trans1)
min_result4_trans1 = min(result4_trans1)
m = 0
n = 0
max_sum_result4_trans1 = 0
min_sum_result4_trans1 = 0

for j in range(b):
    if result4_trans1[j] == max_result4_trans1:
        m += 1
        max_sum_result4_trans1 += j
    elif result4_trans1[j] == min_result4_trans1:
        n += 1
        min_sum_result4_trans1 += j

threshold_I1 = (float(max_sum_result4_trans1)+float(min_sum_result4_trans1))/float(m+n)
c = convert_to_binary_image(a, threshold_I1/float(b+1), b)

plt.imshow(c, cmap='gray')
plt.show()

编辑:我使用的图像和我获得的图像可以在这里查看。该文件夹包含以下内容:

  • 原始图像
  • 在 Octave 中实现算法得到的结果
  • 用Python实现算法得到的结果
  • 使用上述算法进行工作的论文的 PDF。他们的结果可以在论文的图 4 中看到。

尽管 Octave 获得的结果不像论文中描述的那样“清晰”,但这种质量水平是我首先尝试通过 Python 实现的。基于尝试调试代码,我发现了以下问题:

  • 如果我将“convert_to_binary_image”作为独立函数调用以进行测试,则它会提供正确的结果,例如

    plt.imshow(convert_to_binary_image(a, trans_thresh[1], b), cmap='gray')

但是,在尝试调试代码时,我尝试在每次迭代中显示图像

for j in range(b):
    value_trans1 = trans_thresh[j]
    binary_image = convert_to_binary_image(a, value_trans1, b)
    result4_trans1.append(euler_number(binary_image))

此迭代中显示的图像与测试时显示的图像不一致,并且类似于获得的最终图像(上面给出的链接)。

  • 在尝试计算欧拉数时,我尝试了两种方法——一种在 OpenCV 中使用“findContours”,另一种在skimage中使用“regionprops” 。我从两者得到的结果不同(OpenCV 为 1,skimage 为 55)。使用 skimage 的方法是

    region = regionprops(label(image, 4)) e = 0 for r in region: e += r.euler_number return e

我将非常感谢有关上述两个问题的评论 - 为“convert_to_binary_image”绘制的图像的不稳定性以及计算欧拉数的正确实现。

4

0 回答 0