您的位置:首页 > 其它

arcengine 空间挂接赋值

2017-02-10 09:36 316 查看

需求说明

    两数据集空间位置重叠部分进行属性赋值,如有图形存在跨图形情况,重叠部分取面积大的图形进行赋值,此方法只对面图形进行赋值(Polygon)。

空间挂接

获得两个对象:
源图形数据集、赋值图形数据集。
IFeatureClass ExSourceFeature, IFeatureClass ExJoinClass。

获得游标
IFeatureCursor mFeatureCursor
遍历图形对象
IFeature mFeature = mFeatureCursor.NextFeature()

通过空间查询获得与当前图形重叠的图形对象
ISpatialFilter mSpatialFilter = new SpatialFilterClass()

mSpatialFilter.Geometry = mFeature.Shape

选择空间查询方式
mSpatialFilter.SpatialRel = esriSpatialRelEnum.esriSpatialRelIntersects

得到挂接数据集中与当前图形重叠的游标
IFeatureCursor mFCursor = ExJoinClass.Search(mSpatialFilter, false)

遍历得到的游标并求出重叠面积(源图形与挂接图形)
ITopologicalOperator mTopoIntersect = mInterF.Shape as ITopologicalOperator;

                    IGeometry mAreaGeo = mTopoIntersect.Intersect(

                        mFeature.Shape, mFeature.Shape.Dimension);

                    IArea mArea = (mAreaGeo as IPolygon) as IArea;

比较上一个重叠面积与本次比较,保留大的面积,并同时存储图形
if (mArea.Area > mMax)

                    {

                        mMax = mArea.Area;

                        mValueGeo = mInterF;

                    }

遍历后如面积、图形与初始值不同,我们则认为挂接数据集存在符合规则的图形,那么可以对源数据集进行赋值
if (mMax != 0 && mValueGeo != null)

{
//对源数据集进行赋值(通过得到的mValueGeo对象)
}

代码

public static void SpatialJoin(IFeatureClass ExSourceFeature, IFeatureClass ExJoinClass)
{
IFeatureCursor mFeatureCursor = ExSourceFeature.Search(null, false);
IFeature mFeature = mFeatureCursor.NextFeature();
if (ExSourceFeature.FeatureType != esriFeatureType.esriFTSimple)
return;
if (mFeature.Shape.GeometryType == esriGeometryType.esriGeometryPolyline)
{
SpatialLineJoin(ExSourceFeature, ExJoinClass);
return;
}
if (mFeature.Shape.GeometryType != esriGeometryType.esriGeometryPolygon)
return;
while (mFeature != null)
{
ISpatialFilter mSpatialFilter = new SpatialFilterClass();
ITopologicalOperator mTOperator = mFeature.Shape as ITopologicalOperator;

try
{ mSpatialFilter.Geometry = mTOperator.Buffer(-0.1); }
catch
{ mSpatialFilter.Geometry = mFeature.Shape; }
mSpatialFilter.SpatialRel = esriSpatialRelEnum.esriSpatialRelIntersects;
IFeatureCursor mFCursor = ExJoinClass.Search(mSpatialFilter, false);
IFeature mInterF = mFCursor.NextFeature();
IFeature mValueGeo = null;
double mMax = 0;
while (mInterF != null)
{
//相交图形
ITopologicalOperator mTopoIntersect = mInterF.Shape as ITopologicalOperator;
IGeometry mAreaGeo = mTopoIntersect.Intersect(
mFeature.Shape, mFeature.Shape.Dimension);
IArea mArea = (mAreaGeo as IPolygon) as IArea;
if (mArea.Area > mMax)
{
mMax = mArea.Area;
mValueGeo = mInterF;
}
mInterF = mFCursor.NextFeature();
}
Release(mFCursor);
if (mMax != 0 && mValueGeo != null)
{
//对源对象进行赋值
//用updatecount进行跟踪,如有赋值情况,做保存处理(因保存处理花费时间较长,如不存在更新则略过保存)
if (updatecount > 0)
mFeature.Store();
}
mFeature = mFeatureCursor.NextFeature();
}
Release(mFeatureCursor);
}

期间产生的问题

1.分离出Polygon,面积转换只能在面图层内进行。GeometryType类型为esriGeometryPolygon。
2.FeatureType类型为esriFTSimple,牵涉到Annotion时过滤使用。
3.资源无效。游标没有释放造成,通过Marshal.ReleaseComObject释放游标(IFeatureCursor)。
4.ITopologicalOperater buffer异常,此方法buffer值在某些区间内不能使用(怀疑与图形大小及图形面积有关)。
解决方法参考:
点击打开链接

5.大量数据复制报 0x80040239 错误,
参考:点击打开链接正在解决当中。

存在问题

1.没有考虑投影问题。
2.没有考虑面文件外其他Geometry类型。
3.赋值部分花费时间太长,通过现有赋值方法影响效率,需要进一步改进。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息