水平集的核心思想是:通过高维函数曲面来表达低维的演化曲线或曲面,即将演化(变化)的曲线或曲面(界面)用高维水平集函数的零水平集来间接表达,将演化曲线或曲面的演化方程转化为高维水平集函数的演化偏微分方程,通过求解关于水平集函数的方程来捕捉运动边界面。该方法可方便地扩展到任意维空间。目前关于水平集的一种应用是将水平集方法与活动轮廓模型(又称“主动轮廓模型”)结合,用水平集方法来求解活动轮廓模型得到的偏微分方程。
既然讲到水平集,那什么是水平集呢?通俗的说,水平集其实就是水平切面上的一个集合。水平集的标准定义是:与实数c对应的可微函数f:
的水平集是实点集{(x1,x2,……,xn)|f(x1,x2,……,xn)=c}称可微函数f为水平集函数。为了更便于理解,举个例子,当自变量参数个数n=2时,水平集是一个水平曲线,相当于一个空心球体的切面;当自变量的个数n=3时,水平集是一个水平面,相当于一个实心球体的切面。
为了更好地理解水平集的基本思想,下面再多用几句话介绍一下水平集的基本思想。水平集的基本思想用一句话概括就是:低维到高维的映射。具体地将就是:用n维变量的水平集函数f(n+1)维的水平集描述n维曲线或曲面,即把求解n维描述的演化过程转化为求解n维变量的水平集函数f的演化所导致的水平集的演化过程。目的是通过这种转化,引入变中的相对不变——水平集函数f的水平c不变。
--------------------- 作者:Angeldream123 来源:CSDN 原文:https://blog.csdn.net/Angeldream123/article/details/45648387?utm_source=copy 版权声明:本文为博主原创文章,转载请附上博文链接!
Level Set methods 将低维的一些计算上升到更高一维,把 N 维的描述看成是N+1维的一个水平。好处是: 一 低维时的拓扑变换在高维中不再是一个难题; 二 低维需要不时的重新参数化,高维不需要; 三 高维的计算更精确,更鲁棒; 第四 Level Set 方法可以非常容易的向更高维推广; 最后也是非常重要的一点,上升到高维空间中后,许多已经成熟的算法可以拿过来直接用,譬如偏微分方程的理论及数值化等。但是增加了计算量。
快速步进分割 itk::FastMarchingImageFilter
水平集的一个重要的性质就是他们不需要任何额外辅助来融合几个起点的自然能力。
需要用户输入一个种子点或者一个种子点的集合。
===================================================================================
在 FastMarchingImageFilter 的特性中将这个种子集合容器的类型定义为 NodeContainer :
typedef itk::FastMarchingImageFilter< InternalImageType,
InternalImageType > FastMarchingFilterType;
typedef FastMarchingFilterType::NodeContainer NodeContainer;
typedef FastMarchingFilterType::NodeType NodeType;
NodeContainer::Pointer seeds = NodeContainer::New( );
节点作为堆栈变量来创建,并使用一个值和一个 itk::Index 位置来进行初始化:
NodeType node;
const double seedValue = 0.0;
node.SetValue( seedValue );
node.SetIndex( seedPosition );
节点列表被初始化,然后使用 InsertElement( ) 来插入每个节点:
seeds->Initialize( );
seeds->InsertElement( 0, node );
现在使用 SetTrialPoints( ) 方式将种子节点集传递给 FastMarchingImageFilter :
fastMarchingObj->SetTrialPoints( seeds );
===================================================================================
FastMarchingImageFilter 需要用户指定作为输出产生的图像的大小。使用 SetOutputSize( )来完成。
形状检测的水平集分割 itk::ShapeDetectionLevelSetFilter
输入: 一个是图像(itk::Image)形成的最初的一个水平集 - SetInput(**),第二个是一个特征图像(边缘潜在的图像)- SetFeatureImage(**)。
我们可以使用一个FastMarchingImageFilter创建一个最初的水平集作为形状检测水平集分割方法的输入。
利用对原始图像的去噪、梯度计算、sigmoid 来得到潜在的图像边缘特征。
对于大的结构,由于需要花费更长的时间来从起点传播并覆盖这个结构,所以需要大量的迭代器。 通过在对 FastMarchingImageFilter 初始化时多设置几个种子点,可以大大地减轻这个缺点。 这将产生一个与被分割对象的形状更接近的一个最初的水平集,迭代次数也会见减少。
测地线动态轮廓 itk::GeodesicActiveContourLevelSetImageFilter
GAC模型借用了水平集,结合经典的active contour 模型,以图像的梯度为驱动力,在图像梯度最大处,达到收敛。其解决了传统的AC不能处理变形过程中拓扑的变化,如不能处理多物体检测,以及需要对参数的预设置等问题。但是,其在处理模糊图像,或者纹理图像时,效果还是不理想。
来自 <https://blog.csdn.net/hanzihan123/article/details/38441381>
增加第三个水平对流系统扩展了 itk::ShapeDetectionLevelSetImageFilter 的功能。
参数的设置需要实验结合具体的数据获取,所以实际的应用中需要通过用户交互来调节参数。
阈值水平集分割 itk::ThresholdSegmentationLevelSetImageFilter
目的是定义一个亮度值的范围来对相关的组织类型进行分类,然后求出对那个亮度范围基于水平集等式上的传播系数。
可以从 FeatureImage 输入 g 同 UpperThreshold 值 U 和 LowerThreshold 值 L 计算出等式的传播系数 P 。
如图所示阐述了传播系数函数。在g中的亮度值在L和H之间是正数值P,而在亮度范围之外是负数值P。
使用水平集方法,平滑可以防止不好的分割效果。
该方法的输入:一个是水平集,一个是特征图像(附带的示例中特征图像就是原图像)。
这个滤波器也不需要使用水平对流系数(SetPropagation() 和 SetCurvatureScaling())。可设置为1.0.
Canny 边缘水平集分割 itk::CannaySegmentationLevelSetImageFilter
定义了一个速率系数用来最小化一个图像中 Canny边缘的距离。最初的水平集移动穿越一个梯度水平对流领域直到它锁定在这些边缘上。
这个滤波器可以对区域生长分割的结果做优化 (示例就是用ThresholdSegmentationLevelSet 的结果作为 CannySegmentationLevelSet 的输入)。
定义的两个系数是: advection \ propagation 这两项。
该方法的输入: 一个是水平集,一个是特征图像(他的 propagation 和 advection 项已经被设置)。对于特征图像一般会进行去噪工作。
SetVariance() - 设置对输入图像进行高斯平滑的数目。方差为高斯滤波函数的方差
SetThreshold() - 设置允许输出图像的最小值,这个阈值常常被用来设置·Canny边缘检测, Canny边缘检测经过梯度下降它的值会小于一个特定值。 Canny的阈值为各个坐标方向的梯度值的均方值
SetIsoSurfaceValue() - 对于初始化输入图像指定一个表面的等值面的数值是非常重要的。
再设定一个等值面后,将会再处理图像之前对原图的每个像素减去等值面这个值,而等值面是小于但接近与图像中感兴趣部分的灰度值的。也就是说你要知道你感兴趣部分的灰度值是什么,然后再设置等值面的值。像Threshold Segmentation level set image filter是根据图像原有的灰度信息来设置阈值空间的,所以这里不对原图像的灰度值进行改变,直接设置为0 也是可以的。
拉普拉斯水平集分割 itk::LaplacianSegmentationLevelSetImageFilter
定义了一个基于图像中第二派生特征的速率系数
这个滤波器可以对区域生长分割的结果做优化 (示例就是用ThresholdSegmentationLevelSet 的结果作为 LaplacianSegmentationLevelSet 的输入)。
该方法的输入: 一个是水平集,一个是特征图像。
使用拉普拉斯的一个很好的性质就是计算中没有自由参数。
他的使用和 CannySegmentationLevelSet 很类似。
测地线主动轮廓法itk::GeodesicActiveContourLevelSetImageFilter
因为在实际的解剖过程中解剖结构的形状、位置、方位通常是事先知道的,利用形状来支持水平集分割。
该方法的输入:第一个是 itk::Image形成的一个最初的水平集,第二个是特征图像。这个特征图像是一个边缘潜在图像,基本和 ShapeDetectionLevelSetImageFilter有一样的规则。这个GAC示例比SD的示例配置参数要小,忽略了很多多余的描述,两个示例很类似。
这个流水线的第一步就是平滑(CurvatureAnisotropicDiffusionImageFilter)。
平滑之后的 图像输入到 GradientMagnitudeRecursiveGaussianImageFilter ,然后用 SigmoidImageFilter生成边缘潜在的图像(edge potential image)。
输入用户提供的种子点 给 FastMarchingImageFilter然后可以计算出距离映射图。从这个图减去一个常数来获取一个代表最初轮廓的水平集,这个水平集在输入到 GeodesicActiveContourLevelSetImageFilter. 最后这个类生成一个水平集。通过 BinaryThresholdImageFilter 输出一个二值图像来代表被分割的物体。
形状引导测量主动轮廓分割 itk::GeodesicActiveContourShapePriorLevelSetImageFilter.cxx
该方法的输入:第一个是 itk::Image形成的一个最初的水平集,第二个是一个表示图像潜在特征的特征图像。
示例中 itk::ChangeInformationImageFilter来简化形状姿态的估计;
itk::BoundedReciprocalImageFilter来产生边缘潜在的图像;
itk::PCAShapeSignedDistanceFunction 表示一个统计形状模式;
itk::Eular2DTransform 用来表示形状的姿态;
对每个迭代器,当前最合适形状是从边缘潜在图像和当前轮廓估计而来的。
不同的水平集方法,输入不同、预处理方法的选择、设置参数的不同、种子点的选择都是需要注意的地方。
我感觉重要的是选择适合你目的的方法和参数,这个应该是需要通过大量的对比实验得出的结论。但是不能保证适合于所有的情况。