基于C#的ArcEngine二次开发48:点是否落在实体上检查

目录

1 基于选择集的要素实体检查

1.1 基于AGNP层建立选择集

1.2 基于要素类创建multipart要素

1.3 选择集建立与剔除

2 基于空间相离原理的实体检查

2.1 空间相离判断

2.2 逐图层判断

3 导出选择集

3.1 创建导出要素类

3.2 根据选择集导出要素

3.3 导出单个要素


在数据检查过程中,我们需要点要素是否落在实体上进行检查处理,本文针对这个需求介绍两种实现思路

背景依托:我们需要检查AGNP层的AK和BB点与RESA/RESP/RESL是否实体对应关系

思路:首先将需要进行实体要素检查的要素聚合呈multipart要素,然后与AGNP层进行逻辑运算,最终选出不再实体上的AK或BB

1 基于选择集的要素实体检查

该思路为先基于AGNP层所有要素点建立选择集,然后用multipart要素与该选择集求交运算,减去相交的部分,再从最终结果中筛选出CLASS为AK/BB的要素。

1.1 基于AGNP层建立选择集

如果在AO开发,需现将IFeatureClass转化为IFeatureLayer进行运算:

IFeatureLayer pFeatureLayer = new FeatureLayerClass();
pFeatureLayer.FeatureClass = agnpFeatureClass;

IFeatureSelection pSelection = pFeatureLayer as IFeatureSelection;

如果在Addins下,直接读取IFeatureLayer

        /// <summary>
        /// 根据图层名找到图层 
        /// </summary>
        /// <param name="pMap">地图名称</param>
        /// <param name="layerName">图层名称</param>
        /// <returns>未找到图层返回null,找到图层返回目标图层</returns>
        public static IFeatureLayer GetLayerByName(IMap pMap, string layerName)
        {
            for(int i = 0; i < pMap.LayerCount; i++)
            {
                if(pMap.getLayer(i).Name == layerName)
                {
                    return pMap.getLayer(i) as IFeatureLayer;
                }
            }
            return null;
        }

更多信息参见:基于C#的ArcEngine二次开发32:属性sql查询语句与IMap,ILayer,IFeatureLayer,IFeatureClass关系

1.2 基于要素类创建multipart要素


        /// <summary>
        /// 获取空间参考
        /// </summary>
        /// <returns></returns>
        private ISpatialReference GetSpatialReference(IFeatureClass in_FeatureClass)
        {
            IGeoDataset pGeoDataset = in_FeatureClass as IGeoDataset;
            ISpatialReference pSpatialReference = pGeoDataset.SpatialReference;
            return pSpatialReference;
        }
 
        /// <summary>
        /// 合并几何体
        /// </summary>
        /// <returns></returns>
        private IGeometry GetMergeGeometry(IFeatureClass in_FeatureClass)
        {
            IGeometryBag pGeometryBag = new GeometryBag() as IGeometryBag;
            pGeometryBag.SpatialReference = GetSpatialReference(in_FeatureClass);

            IGeometryCollection pGeometryCollection = pGeometryBag as IGeometryCollection;
 
            // 属性过滤
            IQueryFilter pQueryFilter = new QueryFilter();
            pQueryFilter.WhereClause = "GB = 310200 or GB = 310500";
 
            // 要素游标
            IFeatureCursor pFeatureCursor = in_FeatureClass.Search(pQueryFilter, true);
            IFeature pFeature = pFeatureCursor.NextFeature();
            if (pFeature == null)
            {
                return null;
            }
 
            // 遍历游标
            object missing = Type.Missing;
            while (pFeature != null)
            {
                pGeometryCollection.AddGeometry(pFeature.ShapeCopy, ref missing, ref missing);
                pFeature = pFeatureCursor.NextFeature();
            }
            Marshal.ReleaseComObject(pFeatureCursor);
 
            // 合并要素
            ITopologicalOperator pTopologicalOperator = null;
            if (in_FeatureClass.ShapeType == esriGeometryType.esriGeometryPoint)
            {
                pTopologicalOperator = new Multipoint() as ITopologicalOperator;
                pTopologicalOperator.ConstructUnion(pGeometryCollection as IEnumGeometry);
            }
            else if (in_FeatureClass.ShapeType == esriGeometryType.esriGeometryPolyline)
            {
                pTopologicalOperator = new Polyline() as ITopologicalOperator;
                pTopologicalOperator.ConstructUnion(pGeometryCollection as IEnumGeometry);
            }
            else
            {
                pTopologicalOperator = new Polygon() as ITopologicalOperator;
                pTopologicalOperator.ConstructUnion(pGeometryCollection as IEnumGeometry);
            }
            return pTopologicalOperator as IGeometry;
        }

关于multipart更多信息,参见:

1.3 选择集建立与剔除

public ISelectionSet selectSubtract(IFeatureClass agnpFeatureClass, string[] pFeatureClassNames)
{
    
    IFeatureLayer pFeatureLayer = new FeatureLayerClass();
    pFeatureLayer.FeatureClass = agnpFeatureClass;
    IFeatureSelection pSelection = pFeatureLayer as IFeatureSelection;
    pSelection.SelectFeatures(null, ESRI.ArcGIS.Carto.esriSelectionResultEnum.esriSelectionResultNew, false);

    //设置查询条件,如果表达式错误会报异常信息
    ISpatialFilter queryFilter = new QueryFilterClass();

    //读取RESA/RESL/RESP层
    for(int i = 0; i < pFeatureClassNames.Length; i++)
    {
        IFeatureClass pFeatureClass = (srcWorkspace as IFeatureWorkspace).OpenFeatureClass(pFeatureClassNames[i]);

        IGeometry pGeometry = GetMergeGeometry(pFeatureClass);

        //设置空间查询条件
        queryFilter.Geometry = pGeometry;
        queryFilter.GeometryField = "SHAPE";
        queryFilter.SpatialRel= esriSpatialRelEnum.esriSpatialRelIntersects;

        //选择集过滤
        pSelection.SelectFeatures(queryFilter, ESRI.ArcGIS.Carto.esriSelectionResultEnum.esriSelectionResaultSubtract, false);
    }
    ISelectionSet pSelectionSet = pSelection.SelectionSet;
    //导出代码
}

2 基于空间相离原理的实体检查

2.1 空间相离判断

//判断AGNP层要素与构造的复合要素是否相离
private bool spatialdDisjiont(IFeature pFeature, IGeometry multipartGeometry)
{
    IReleationalOperation pRelOpr = pFeature.ShapeCopy;
    return pRelOpr.Disjoint(multipartGeometry);
}

2.2 逐图层判断

private void check(IWorkspace srcWorkspace, IGeometry multipartA, IGeometry multipartS, IGeometry multipartP)
{
    IFeatureWorkspace pFeatureWorkspace = srcWorkspace as IFeatureWorkspace;
    IFeatureClass pRefFeatureClass = pFeatureWorkspace .OpenFeatureClass(refFeatureClassName);
    IFeatureCursor pCursor = pRefFeatureClass.Search(null, false);
    IFeature pFeature = pCursor.NextFeature();
    while(pFeature != null)
    {
        if(spatialRel(pFeature, multipartA) && spatialRel(pFeature, multipartL) && spatialRel(pFeature, multipartP))
        {
            exportSingleAKorBB(pFeature);
        }
        pFeature = pCursor.NextFeature();
    }
}    

3 导出选择集

3.1 创建导出要素类

private void CreateFeatureClass(string strShapeFolder, string refFeatureClassName,string ouFeatureClassName)
{
    IWorkspaceFactory pWSF = new FileGDBWorkspaceFactoryClass();
    IWorkspace srcWorkspace = pWSF.OpenFromFile(strShapeFolder,0);
    IFeatureWorkspace pFeatureWorkspace = srcWorkspace as IFeatureWorkspace;
    IFeatureClass pRefFeatureClass = pFeatureWorkspace .OpenFeatureClass(refFeatureClassName);

    IGeoDataset refGeodataset = pRefFeatureClass as IGeoDataset;
    IFields pFields = refGeodataset.Fields;

    IFeatureDataset pWorkDataset = pFeatureWorkspace.OpenFeatureDataset("MainDataFrame");
    IWorkspace2 pWorkspace2 = pWorkDataset.Workspace as IWorkspace2;
    if(pWorkspace2.get_NameExists(esriDatasetType.esriDTFeatureClass, ouFeatureClassName))
    {
         IFeatureClass pDelFeatureClass = pFeatureWorkspace .OpenFeatureClass(ouFeatureClassName);
        IDataset pDS = pDelFeatureClass as IDataset;
        pDS.Delete();
    }
    pWorkDataset.CreateFeatureClass(ouFeatureClassName, pFields, null, null, esriFeatureType.esriFTSimple, "Shape", "");
}

3.2 根据选择集导出要素

exportSelectionSetAKorBB(IFeatureClass ouFeatureClass, ISelectionSet pSelectinset, string type)
{
    ICursor pCursor;
    pSelectinset.Search(null, false, out pCursor);
    IFeatureCursor pFeatureCursor = pCursor as IFeatureCursor;
    IFeature pFeature = pFeatureCursor.NextFeature;

    while(pFeature != null)
    {
        if(pFeature.get_Value(pFeature.Fields.FindField("STACOD")).ToString() != "删除" && pFeature.get_Value(pFeature.Fields.FindField("CLASS")).ToString() != type)
        {
            IFeature ouFeature = ouFeatureClass.CreateFeture();
            for(int ii = 0; ii < ouFeatureClass.Fields.FieldCount; ii++)
            {
                string fiedldName = pFeature.Fields.get_Field(ii).Name;
                switch(ouFeature.Fields.get_Field(ii).Name)
                {
                    case "OBJECTID": break;
                    case "CREATED_USER": break;
                    case "CREATED_DATE": break;
                    case "CREATED_EDITED_USER": break;
                    case "CREATED_EDITED_DATE": break;
                    default :
                        ouFeature.set_Value(ii, pFeature.get_Value(ii));
                        break;
                }
            }
            ouFeature.Shape = pFeature.ShapeCopy;
            ouFeature.Store();
        }
        pFeature = pFeatureCursor.NextFeature;
    }
}

3.3 导出单个要素

exportSingleAKorBB(IFeatureClass ouFeatureClass, IFeature pFeature, string type)
{
        if(pFeature.get_Value(pFeature.Fields.FindField("STACOD")).ToString() != "删除" && pFeature.get_Value(pFeature.Fields.FindField("CLASS")).ToString() != type)
        {
            IFeature ouFeature = ouFeatureClass.CreateFeture();
            for(int ii = 0; ii < ouFeatureClass.Fields.FieldCount; ii++)
            {
                string fiedldName = pFeature.Fields.get_Field(ii).Name;
                switch(ouFeature.Fields.get_Field(ii).Name)
                {
                    case "OBJECTID": break;
                    case "CREATED_USER": break;
                    case "CREATED_DATE": break;
                    case "CREATED_EDITED_USER": break;
                    case "CREATED_EDITED_DATE": break;
                    default :
                        ouFeature.set_Value(ii, pFeature.get_Value(ii));
                        break;
                }
            }
            ouFeature.Shape = pFeature.ShapeCopy;
            ouFeature.Store();
        }
}
 
©️2020 CSDN 皮肤主题: 编程工作室 设计师:CSDN官方博客 返回首页
实付 49.90元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值