GP开发示例:数据库去重

这个例子专业讲解基于ArcEngine使用GP开发的过程及遇到的问题。更多GP使用方法:GP使用心得

功能需求:现在外业第一次数据(简称调绘.mdb)和第二次数据(简称检查.mdb)有重复。第二次是在第一次的基础上进行的,即如果调绘.mdb中LCA层有365个要素,检查时发现错误,就删除了11个错误,并新增了43个,共408个,检查.mdb相对于调绘.mdb实际上有354个重复,现在要将重复的删除,mdb中包括点、线、面三种类型的要素类。

软件实现:在ArcGIS里利用工具可以实现,使用按空间位置查询,找出重复的,然后删除即可;由于每个mdb中的要素图层比较多,所以可以使用批处理,批处理时填写参数可以利用Excel快速进行。但是,mdb较多,路径各不相同,图层较多,操作起不比较费时。

程序实现

1.首先确定用什么工具来实现(先在ArcGIS里做一次):利用空间位置查询选择重复的要素,开启编辑器,删除!

2.设计界面,我每写一个功能,都要把界面整理一下,因为我不想让它很丑就出去见人。这里使用DotNetBar,节省了相当多的时间。

3.因为是直接对数据库进行操作,所以首先就要遍历数据中的要素图层,一般做法是利用GP的ListFeatureClasses方法。

GP.SetEnvironmentValue("workspace", moreDBPath.Trim());
IGpEnumList pGpEnumList = GP.ListFeatureClasses("", "", "");
string strFC = pGpEnumList.Next();
while (strFC != "")
{
    System.Windows.Forms.Application.DoEvents();
    Console.WriteLine(strFC);
    strFC = pGpEnumList.Next();
}

选择遍历数据库没有问题!

4.利用按位置选择

SelectLayerByLocation SLBL = new SelectLayerByLocation();
SLBL.in_layer = moreDB + "\\" + strFC;
SLBL.select_features = referDB + "\\" + strFC;
SLBL.overlap_type = "ARE_IDENTICAL_TO";
GPClass.Execute(SLBL); //这里使用了自定义的GPClass类,可以直接使用GPExecute

报错ERROR 000368,去官网帮助一查,竟然没有368,这是为什么?但从相邻错误信息来看,应该是哪个参数无效!

再去官网看了按空间位置查询的帮助文档。它说:输入必须是要素图层;不可以是要素类。要素图层?要素类?以前一直把它们看成是一种意思,于是去查一下了帮助,长知识了。

结果Python的示例代码,使用了MakeFeatureLayer来创建要素图层。

//创建要素图层
MakeFeatureLayer MFL = new MakeFeatureLayer();
MFL.in_features = moreDB + "\\" + strFC;
MFL.out_layer = strFC + @"_Lyr";
GPClass.Execute(MFL);

//按位置选择
SelectLayerByLocation SLBL = new SelectLayerByLocation();
SLBL.in_layer = strFC + @"_Lyr";
SLBL.select_features = referDB + "\\" + strFC;
SLBL.overlap_type = "ARE_IDENTICAL_TO";
GPClass.Execute(SLBL);

GP执行成功,虽然还看不到效果。因为MakeFeatureLayer是临时图层,程序结束就没有了,需要将它导出来:

//复制要素导出
CopyFeatures CF = new CopyFeatures();
CF.in_features = strFC + @"_Lyr";
CF.out_feature_class = resultDB + "\\" + strFC;
GPClass.Execute(CF);

现在的问题是是选择类型是ARE_IDENTICAL_TO,如果输入图层中的要素与某一选择要素相同(就几何而言),则会选择这些要素。生成的mdb是重复那一部分,而需要的结果是不重复的那一部分。在ArcGIS里可以通过切换选择来操作。于是想,先把它全部选中,然后将重复的移除。代码:

//创建要素图层
MakeFeatureLayer MFL = new MakeFeatureLayer();
MFL.in_features = moreDB + "\\" + strFC;
MFL.out_layer = strFC + @"_Lyr";
GPClass.Execute(MFL);

//选择所有
SelectLayerByAttribute SLBA = new SelectLayerByAttribute();
SLBA.in_layer_or_view = strFC + @"_Lyr";
GPClass.Execute(SLBA);

//按位置选择(移除)
SelectLayerByLocation SLBL = new SelectLayerByLocation();
SLBL.in_layer = strFC + @"_Lyr";
SLBL.select_features = referDB + "\\" + strFC;
SLBL.overlap_type = "ARE_IDENTICAL_TO";
SLBL.selection_type = "REMOVE_FROM_SELECTION";
GPClass.Execute(SLBL);

//复制要素
CopyFeatures CF = new CopyFeatures();
CF.in_features = strFC + @"_Lyr";
CF.out_feature_class = resultDB + "\\" + strFC;
GPClass.Execute(CF);

终于实现了。

5.为了增加用户的体验,重写在了一个类,并把新建一个线程来处理:

string referDB = "";
string moreDB = "";
string resultDB = "";
ProgressBarX progress = null;
public NoRepeatClass(string _referDB, string _moreDB, string _resultDB, ProgressBarX _progress)
{
    referDB = _referDB;
    moreDB = _moreDB;
    resultDB = _resultDB;
    progress = _progress;

    Thread MyThreadOne = new Thread(new ThreadStart(MainFun));
    MyThreadOne.Name = "NoRepeat";
    MyThreadOne.IsBackground = true;
    MyThreadOne.Start();
}

private void MainFun()
{
 //主程序代码
}

6.为了让用户知道处理的进度,于是添加了进度条,并更新内容为当前处理图层的名称。但这里,不能直接在一个线程里设置主线程的控件属性,于是找了一个函数:

#region 设置控件参数
/// <summary>
/// 设置控件参数
/// </summary>
/// <param name="oControl">控件</param>
/// <param name="propName">参数名称</param>
/// <param name="propValue">参数值</param>
delegate void SetControlValueCallback(Control oControl, string propName, object propValue);
public static  void SetControlPropertyValue(Control oControl, string propName, object propValue)
{
    if (oControl.InvokeRequired)
    {
        SetControlValueCallback d = new SetControlValueCallback(SetControlPropertyValue);
        oControl.Invoke(d, new object[] { oControl, propName, propValue });
    }
    else
    {
        Type t = oControl.GetType();
        System.Reflection.PropertyInfo[] props = t.GetProperties();
        foreach (System.Reflection.PropertyInfo p in props)
        {
            if (p.Name.ToUpper() == propName.ToUpper())
            {
                p.SetValue(oControl, propValue, null);
            }
        }
    }
}
#endregion

目前的效果如下:

7.为了提高操作效率,增加了路径拖放功能,下面是拖放类:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.IO;

namespace GPTools
{
    class DragClass
    {
        private  Control control;
        private string fileType = "";

        public DragClass(Control _control,string _fileType)
        {
            //如果控件为空
            if (_control == null)
            {
                return;
            }
            control = _control;
            fileType = _fileType;

            //设置是否可以拖放
            control.AllowDrop = true;

            //定义拖放事件
            control.DragEnter += new DragEventHandler(control_DragEnter);
          ontrol.DragDrop += new DragEventHandler(control_DragDrop);

        }

        private void control_DragEnter(object sender, DragEventArgs e)
        {
            if (e.Data.GetDataPresent(DataFormats.FileDrop))
            {
                e.Effect = DragDropEffects.Copy;
            }
        }

        private void control_DragDrop(object sender, DragEventArgs e)
        {
            string[] files = (string[])e.Data.GetData(DataFormats.FileDrop);
            foreach (string file in files)
            {
                //判断文件类型
                if (Path.GetExtension(file) == fileType)
                {
                    Console.WriteLine(file);
                    control.Text = file;
                }
            }
        }
    }
}

在初始化主程序后实例化拖放类,一旦拖放就会触发DragEnter事件和DragDrop事件:

DragClass dg = new DragClass(this.txbReferDB, ".mdb");
DragClass dg2 = new DragClass(this.txbMoreDB, ".mdb");

8.因为我们只遍历了检查.mdb中的图层,万一调绘.mdb中没有对应图层怎么,所以,我们得检查,如果没有则跳过。

//创建要素图层
//……

//检查数据
object dt = "";
if (GPClass.GP.Exists(referDB + "\\" + strFC, ref dt))
{
    //3.选择所有
    //4.按位置选择(移除)
}
//复制要素
//……

9.为了更准确的统计操作时间,添加了计时功能。效果图如下:

参考:http://bbs.esrichina-bj.cn/esri/viewthread.php?tid=50540

时间: 2024-07-29 23:04:37

GP开发示例:数据库去重的相关文章

PHP 开发中数据库及其相关软件的选型考虑

PHP(PHP培训 php教程 ) 版本各异,已经停止升级开发的有 4.0 系列的 4.4.x,但现在还有部分生产环境在跑这个版本,需要继续维护代码.PHP 5.0 系列是现在开发和应用的主流版本,有 5.1.x 和 5.2.x 系列.PHP 6.0 目前还是试用版本,用 PHP 开发软件产品的人现在可以预先作兼容性测试. PHP 支持的数据库(数据库培训 数据库认证 )很多,包括 PHP 本身自带的数据库驱动组件,例如 mysql.dll.oci_oracle 等.PHP 从 5.1 版本以后

移动前端开发之数据库操作篇

在移动平台开发中,经常会有大数据存储与交互的操作,在以webkit为内核的浏览器中,提供了一个叫作WEBSQL的数据库.这让我们前端也可以像php等程序语言一样,进行数据库的读写操作.Web Storage存储本地数据的方法目前可以在许多主流浏览器.平台与设备上实现,与之相关的API也已经标准化,但是,Web Storage存储空间是有5MB,键值存储的方式带来诸多不便,未来本地存储也不仅仅是这一种方法.其中最为熟知的就是Web SQL数据库,它内置SQLite数据库,对数据库的操作可以通过调用

Spring+Mybatis开发示例

写下来留个纪念(^~^)大神可飘过 1,实现Spring+Mybatis+数据源的配置 2,实现枚举到数据库TINYINT类型的转换 3,slf4j日志配置方法 4,数据库增+删+改+查操作 5,实现效果界面+项目配置目录树       6,关键代码: a)控制器 package com.fresh.lyh.simple.controller; import com.fresh.lyh.simple.model.Simple; import com.fresh.lyh.simple.model.

windows phone 8.1开发SQlite数据库操作详解

原文出自:http://www.bcmeng.com/windows-phone-sqlite1/ 本文小梦将和大家分享WP8.1中SQlite数据库的基本操作:(最后有整个示例的源码)(希望能通过本站广告支持小梦,谢谢!) 建立数据库 增加数据 删除数据 更改数据 查询数据 (注:为了让每个操作都能及时显示在UI上,所以进行了数据绑定.数据绑定会在后面文章专门讲解,先给出数据类Note,代表一个笔记.含有Name 和content  属性.其代码如下:如果不清楚,我会在之后讲解): names

IOS开发之数据库FMDB

IOS开发之数据库FMDB 1.简介 需求作用:如果需要保存大量的结构较为复杂的数据时候, 使用数据库, 例如交规考试项目 常用的数据库: (1)Microsoft SQL Server 2000/2008:中小企业使用较多 (2)Oracle:比较复杂, 大企业使用较多 (3)Mysql数据库:网站使用较多 (4)sqlite:本地数据库, 访问数据足够快, 直接访问文件  足够简单, 功能相对其他数据库软件不是特别齐全, 足够用了  足够小, 系统不超过1M, 适合在移动端上使用 2. Me

asp开发出现数据库引擎错误: &#39;80040e14&#39;

几分钟写完一个程序,在浏览器上进行测试的时候却总是出现Microsoft JET Database Engine  '80040e14'.网上搜了许多资料,自己又定位程序出错的位置进行异常仔细的检查,可是仍然没有任何进展..真真是分分钟都有想要放弃重新开始写得冲动.. 网上给出的解决方案大致就是修改数据库访问权限,还有就是程序语法错误(大多数都是这种情况),还有一些原因,不过我敢确定我不是在这些方面出现了问题,于是便不做任何计较.根据我个人的情况,报错的位置大概就是open数据库的时候,不过我敢

[转]Net Framework引路蜂地图开发示例

From:http://www.2cto.com/kf/201207/140421.html 引路蜂地图也提供对.Net Framework平台的支持,可以开发桌面地图应用,由于Mono C#的跨平台特性,使用Visual Studio 和Mono引路蜂地图开发包开发的地图应用可以运行于Windows ,Lunix,Unix,Mac OS等平台.开发桌面应用比开发移动应用要容易的多,屏幕,内存等方面都比移动平台要宽裕的多.下面使用一个简单的应用来介绍一下.Net Framework引路蜂地图开发

SqlServer示例数据库Northwind(一)——实体关系

在学习Spss统计分析.EA画实体关系图.PowerDesigner画数据库模型图等时,苦于找不到一个好的实例.由于实际工作中项目使用的表结构属于公司的商业保密内容,且在和大家交流时,其结构大家也不熟悉:而使用简单创建的Teacher.Student.Class等数据模型时,建表.录数据也是一个麻烦事:使用SqlServer的示例数据库正好,大伙都熟悉,又是现成的. 很多书籍.教程都使用Northwind数据库作为模型,但我一直对它不甚了解,今天特意下载后了解了一下,现在简单的记录下笔记,以后依

浅谈数据库去重

关于sql去重,我简单谈一下自己的简介,如果各位有建议或有不明白的欢迎多多指出.推荐网址:www.4-yecao.com 关于sql去重最常见的有两种方式:DISTINCT和ROW_NUMBER(),当然了ROW_NUMBER()除了去重还有很多其他比较重要的功能,一会我给大家简单说说我自己在实际中用到的. 假如有张UserInfo表,如下图: 现在我们要去掉完全重复的数据:SELECT DISTINCT * FROM dbo.UserInfo结果如下图: 但是现在有个新的需求,要把名字为‘张三