一共4个函数,其中外部直接调用CompareLinePolygon即可得到结果,另外3个函数是内部处理逻辑。
/// <summary>
/// 比较面图层与线图层是否完全重合
/// </summary>
/// <param name="lineLayer"></param>
/// <param name="polygonLayer"></param>
/// <returns></returns>
public bool CompareLinePolygon(ILayer lineLayer, ILayer polygonLayer)
{
IFeatureClass polygonClass = (polygonLayer as IFeatureLayer).FeatureClass;
IFeatureClass lineClass = (lineLayer as IFeatureLayer).FeatureClass;
//一个面至少对应一个线,有挖空区域的面则可能对应多个线
if (polygonClass.FeatureCount(null) > lineClass.FeatureCount(null))
{
return false;
}
IFeatureCursor pCursor = null;
try
{
pCursor = lineClass.Search(null, false);
IFeature lineFeature = pCursor.NextFeature();
//遍历线要素
while (lineFeature != null)
{
//获取与线要素相交的面要素
IFeatureCursor polygonCursor = GetPolygonFeatures(lineFeature, polygonClass);
if (polygonCursor == null) return false;
//判断相交的面要素中,是否有与线要素边界完全重合的
if (HasSameFeature(lineFeature, polygonCursor) == false) return false;
lineFeature = pCursor.NextFeature();
}
return true;
}
catch (Exception ex)
{
return false;
}
finally
{
ComReleaser.ReleaseCOMObject(pCursor);
}
}
/// <summary>
/// 获取与线要素相交的所有面要素
/// </summary>
/// <param name="lineFeature"></param>
/// <param name="polygonClass"></param>
/// <returns></returns>
private IFeatureCursor GetPolygonFeatures(IFeature lineFeature, IFeatureClass polygonClass)
{
IFeatureCursor pCursor = null;
try
{
IGeometry line = lineFeature.ShapeCopy;
ISpatialReference pSRPolygon = (polygonClass as IGeoDataset).SpatialReference;
line.Project(pSRPolygon);
ISpatialFilter pFilter = new SpatialFilterClass();
pFilter.Geometry = line;
pFilter.GeometryField = polygonClass.ShapeFieldName;
pFilter.SpatialRel = esriSpatialRelEnum.esriSpatialRelIntersects;
pCursor = polygonClass.Search(pFilter, false);
return pCursor;
}
catch (Exception ex)
{
return null;
}
}
/// <summary>
/// 判断线要素中是否有与面要素边界重合的
/// </summary>
/// <param name="polygonFeature"></param>
/// <param name="lineCursor"></param>
/// <returns>如果有一个线要素与面要素的边界重合,则返回ture;否则返回false</returns>
private bool HasSameFeature(IFeature pFeature, IFeatureCursor pCursor)
{
bool bHasSame = false;
IFeature targetFeature = pCursor.NextFeature();
while (targetFeature != null)//遍历线要素
{
if (IsSuperPosition(targetFeature, pFeature) == true)
{
bHasSame = true;//存在一个线要素,与面要素边界重合
break;
}
targetFeature = pCursor.NextFeature();
}
ComReleaser.ReleaseCOMObject(pCursor);
return bHasSame;
}
/// <summary>
/// 判断面要素与线要素边界是否重合
/// </summary>
/// <param name="polygonFeature"></param>
/// <param name="lineFeature"></param>
/// <returns>重合返回ture,不重合返回false</returns>
private bool IsSuperPosition(IFeature polygonFeature, IFeature lineFeature)
{
ITopologicalOperator pTopoOper = polygonFeature.ShapeCopy as ITopologicalOperator;
pTopoOper.Simplify();
IGeometry boundary = pTopoOper.Boundary;
IGeometry pSrcLine = lineFeature.ShapeCopy;
ITopologicalOperator pSrcLineTopoOper = pSrcLine as ITopologicalOperator;
pSrcLineTopoOper.Simplify();
//多边形可能由多个Ring组成,所以其边界可能有多个线构成,所以pSrcLine<=boundary
//这里用pSrcLine去Difference多边形边界boundary,则得到IsEmpty=true的Geometry
//如果用boundary去Difference线pSrcLine,则得到IsEmpty=false的Geometry
IGeometry pDiffGeo = pSrcLineTopoOper.Difference(boundary);
return pDiffGeo.IsEmpty;//线与面边界重合
}