社会焦点

Kaggle百万美元大赛优胜者:如何用CNN识别CT图像检测肺癌?(2)

字号+ 作者: 来源: 2017-05-07

我的第一个目标是训练一个可作为基础的结节检测器。我先要对正面例子进行过采样,将正反两类的样本比上调到1:20。为了提高模型的泛化能力,我尝试了一些图像增强操作,但是只有一些无损的操作是有用的。最后我用了

  我的第一个目标是训练一个可作为基础的结节检测器。我先要对正面例子进行过采样,将正反两类的样本比上调到1:20。为了提高模型的泛化能力,我尝试了一些图像增强操作,但是只有一些无损的操作是有用的。最后我用了大量的转化操作和所有3D翻转操作。

  设计好分类器后,我想训练一个用于估计恶化程度的回归模型。将肿瘤恶化程度分为从1(很可能不是恶性)到5(很可能是恶性的)。为了强调肿瘤的恶性程度,我将标签平方,范围扩大为从1到25。最开始,我考虑了分阶段的一种方法,用第一个网络来分类节点,然后训练另一个网络估计结节的恶化程度。为了缩短计算时间,我尝试只用一个网络,以多任务学习的方法,同时进行训练这两个任务。当编程实现后,我发现这个方法简单快速,网络的效果也很好。

  通常,神经网络的结构是比赛和案例研究中最重要的成果之一。对于这场比赛,我在神经网络的结构上花费的时间相对较少,因为已经有很多优秀网络可供参考。刚开始我使用了一些简单的VGG网络和Resnet网络的相似结构,但是它们的性能大致相同。然后我尝试用一个预训练好的C3D网络,原有的网络权重根本没有帮助,但直接初始化权重后,这种网络结构的效果很好。基于C3D网络进行若干次调整后,我得到最终的分类评估网络。

  我首先调整了输入大小,设置为32x32x32 mm。这看起来可能太小,但是在后续的网络层中加入一些技巧,发现这种维度的实际效果很好。这个想法是保持一切轻量化,并在比赛结束后再建立一个更大输入维度的网络。但是由于Daniel的网络输入是64x64x64 mm,我决定保持目前的输入大小,使网络的输出互补。接下来我立即对z轴进行平均池化操作,使得每个体素表示2mm的区域。这进一步减少了网络的参数量,并没有影响到精度,因为在大多数扫描中,z轴会比x轴和y轴更粗糙。最后,我在网络顶部引入了64个节点的全连接层。这里,我们不是直接预测恶性肿瘤,而是通过训练图片的中级特征,输出结节的恶化程度。

  Kaggle百万美元大赛优胜者:如何用CNN识别CT图像检测肺癌?

  表2:3D Convnet的网络结构示意图

  有趣的插曲:“奇怪组织”检测器

  看着论坛的帖子,我发现所有的团队都在做类似的工作,我也在寻找一个能直接上手的方法。在观察CT扫描图像时,我发现了一些其他的事情。与LUNA16数据集一样,大部分的工作集中在识别肺结节上。然而,当癌症发展时,它们转变成肺肿块或更复杂的组织。并且我注意到,当扫描图像中有很多“奇怪组织”时,它发展为癌症的概率更大。此外,在很多CT图像中,我的结节探测器没有发现任何结节,这造成了一些很不好的假阴性现象。

  在训练集中有10例存在上述现象,其中的5例为癌症病例。为了解决这些严重的假阴性,在扫描时,需要检测获得奇怪组织的数量。很幸运,在LUNA16数据集上包含了很多这样的样本,所以我很快对数据集进行标记并训练了一个U-net网络。加入奇怪组织检测器后,效果不错,我因此提高了本地CV值和LB上的排名。因为它对于不同的模型提升不同,很难评定实际效果,但我认为它大约提升了0.002-0.005。说实话,我认为这种改进是一个创新性的补充。以下是一些包含有奇怪组织的样本。

  Kaggle百万美元大赛优胜者:如何用CNN识别CT图像检测肺癌?

  图3:带有奇怪组织的CT图像样本。

  肺气肿基本上是由吸烟导致的,我也试图建立一个肺气肿检测器。论坛上的医生都说,当肺气肿存在时,患有癌症的概率升高。有一些简单的算法公布了如何评估CT扫描中肺气肿区域的数量,设置hounsfield单位为950,来扫描CT图像。然而,我应用这种方法后,发现效果并不好。然后我标记了一些例子来训练一个U-net,发现效果不错,但是我的本地CV值没有丝毫提升。我的猜测是,因为肺部出现问题,进行扫描得到数据集中的许多病例,因此很多肺气肿样本没有看做是肺结节和癌症病例。我不能确定这个想法的正确性。

  最后一步:癌症预测

  训练好网络后,下一步是让神经网络检测结节并估计其恶化程度。我建立的CT结节观察器很容易查看网络结果。我觉得神经网络的效果很好:它检测到了许多我完全忽视的结节,而我只看到很少量的假阳性结节。但是还存在一个严重的问题:由于它错过了一些非常大的明显结节,所以影响了对于假阴性的得分,有时使LogLoss升高了3.00。作为尝试,我试图对CT图像进行了两次降采样,看看检测器是否会检测大结节。值得注意的是,它的效果非常好。因此,我调整了网络结构,让网络预测3个尺度,分别为1,1.5和2.0。我觉得值得花这么多的时候来改善这方面的性能。

  Kaggle百万美元大赛优胜者:如何用CNN识别CT图像检测肺癌?

  图4:在缩放1x的左图中,没有很好地检测到大结节;但是在2x放大的右图时,效果较好。矩形的大小表示坚持到的恶性肿瘤。

  鉴于这些数据和一些其他特征,我想训练一个以梯度推进的分类器来预测一年内癌症的发病率,这是比较容易实现的。但是问题在于,排行榜的得分是基于给定的200名患者,这里面意外地包含了大量异常患者。经过一些调整后,我通过交叉验证得到了本地的平均值为0.39-0.40,而排行榜得分在0.44和0.47之间变化。此时很难将排行榜得分与本地CV值相关联。提高了本地CV值可能导致LB评分的降低,反之亦然。

  我花了很多时间来研究本地CV值和LB评分的关系。我没有成功,所以我只使用能同时改进CV值和LB排名的技巧和特征。这是一场两阶段的比赛,而且与实际的训练集相比,第二阶段的数据存在与LB数据集更相似的可能。在这个地方,很多队伍也只能碰运气,结果显示排行榜上的很多队伍模型处于过拟合状态。最后我只使用7个特征来训练梯度推进器,分别是3个尺度下的最大恶性结节及其Z轴的位置和样本中奇怪组织的数量。

  我也融合了两个模型来提高效果。第一个模型是在完整的LUNA16数据集上训练的。第二次,我试图从NDSB训练集中选择明显的阳性样本和假阳性样本,应用主动学习来训练。由于我不是放射科医师,所以我为了保险起见,只选择癌症病例的阳性例子和非癌症病例的阴性例子。我做错了,因为第二个模型比没有额外标注的LUNA16模型更糟糕。通过平均两个模型的输出,对LB排名有了很好的推动作用,并且显著提高了本地CV值。

  与Daniel合作

转载请注明出处。


1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,请转载时务必注明文章作者和来源,不尊重原创的行为我们将追究责任;3.作者投稿可能会经我们编辑修改或补充。

相关文章