博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
C#开发SQLServer的Geometry和Geography存储
阅读量:6375 次
发布时间:2019-06-23

本文共 6471 字,大约阅读时间需要 21 分钟。

原文:

SQL Server2008推出后最大的变化就是提供了支持空间数据存储的Geometry和Geography,这个也是如果将ArcSDE和SQLServer数据库相结合后可以供用户选择的一种数据存储模式,因为SQLServer2008前的数据库版本都是BLOB来存储空间数据对象的,目前没有测试来判断哪个性能更优,但是个人倾向于Geometry和Geography。

使用这两种存储,一个优点就是,使用SQL Server数据库也可以像使用Oracle、PostgreSQL一样,使用SQL来进行操作。

在以前的文章中我们也介绍了关于SQL的操作,但是都是在SQl Server的manger studio里面进行的

相关参考:  

本文介绍的如何使用编程的方式C#来对SQL Server空间数据存储的Geometry和Geography来进行操作。

首先我们需要引用一个Microsoft.SqlServer.Types.dll,

该文件根据32Bit和64Bit的不同分布情况不同

32Bit:C:\Program Files \Microsoft SQL Server\100\SDK\Assemblies

64Bit:C:\Program Files (x86)\Microsoft SQL Server\100\SDK\Assemblies

注意如果你的SQL Server是2008和2012也是有相关区别的。

引用相关dll我们就可以进行开发了

以下代码环境:VS2010,引用dll版本SQL Server2012

using System;using System.Collections.Generic;using System.ComponentModel;using System.Data;using System.Drawing;using System.Linq;using System.Text;using System.Windows.Forms;using Microsoft.SqlServer.Types;using System.Data.SqlClient;using System.Data.SqlTypes;using System.Configuration;namespace SQL{    public partial class Form1 : Form    {        public Form1()        {            InitializeComponent();                      object s= GetSRID("sde101", "sde", "CHINACITYTABLE");        }        //连接串        string connstring = "Data Source=192.168.100.111;Initial Catalog=sde101;Persist Security Info=True;User ID=sde;Password=sde";        //获得数据连接        public SqlConnection GetSQLConnection()        {            try            {                return new SqlConnection(connstring);            }            catch (Exception)            {                return null;            }        }                    //将Geometry对象转换为WKT串        public  void QuerytoWKT()        {            string sql = "select shape from xzq where objectid=45";            SqlGeometry g = GetGeometry(sql);            if (g != null)            {                //以WKT输出                Console.WriteLine(g);            }        }        //获得Geometry对象        ///         /// 直接使用SQL语句获得SQLGeometry对象        ///         ///         /// 
public SqlGeometry GetGeometry(string sql) { try { SqlCommand cmd = GetCommand(sql); SqlDataReader reader = cmd.ExecuteReader(); while (reader.Read()) { SqlBytes sb = reader.GetSqlBytes(0); //Deserialize方法只有引用SQLServer2012的dll才能使用,2008不支持  SqlGeometry g = SqlGeometry.Deserialize(sb); return g; } return null; } catch (Exception e) { return null; } } /// /// 根据WKT串获得SQLGeometry对象 /// /// /// ///
public SqlGeometry GetGeometry(string sWKT, int sSRID) { // var sql = "POLYGON((509827.650 3848402.022,509763.336 3847282.564,509268.926 3847640.308,509827.650 3848402.022))"; SqlChars polyText = new SqlChars(sWKT); return SqlGeometry.STGeomFromText(polyText, sSRID); } public SqlCommand GetCommand(string sql) { SqlConnection conn = GetSQLConnection(); conn.Open(); SqlCommand cmd = new SqlCommand(sql, conn); return cmd; } //增删改直接写上不同的SQL语句即可 public void EditData() { try { string sWKT = "POLYGON((513132.704 3847868.592,513860.309 3846638.277,512682.911 3846598.589,513132.704 3847868.592))"; string sql = "insert xzq (objectid,shape) values(11111,'"+sWKT+"')"; SqlCommand cmd = GetCommand(sql); cmd.ExecuteNonQuery(); } catch (Exception e) { } } //获得相交数据 /// /// Unable to load DLL 'SqlServerSpatial110.dll': 找不到指定的模块。 (Exception from HRESULT: 0x8007007E) /// public void GetIntersections() { try { string sql1 = "select shape from xzq where objectid=86"; string sql2 = "select shape from xzq where objectid=71"; SqlGeometry g1 = GetGeometry(sql1); SqlGeometry g2 = GetGeometry(sql2); //获得相交的图形 SqlGeometry g3 = g1.STIntersection(g2); if (g3 != null) { //以WKT输出 Console.WriteLine(g3); } } catch (Exception e) { } } //获得两点距离 public string GetDistance(SqlGeometry p1, SqlGeometry p2) { return p1.STDistance(p2).ToString(); } /// /// //根据表名获得SRID /// 主要是直接进入GDB_ITEMS表里面获得制定表对象的SRID值 /// GDB_ITEMS表是安装了ArcSDE后才有的表 /// select shape from [sde101].[sde].[CHINACITYTABLE] /// /// /// /// ///
public object GetSRID(string sDatabasename,string sUser,string sTableName) { //如果找不到,返回0 object SRID = null; //如果熟悉ArcSDE的库的表结构,只要是解析相关的XML文件,来获得SRID string sql = "SELECT Definition.value('(/DEFeatureClassInfo/SpatialReference/LatestWKID)[1]','nvarchar(max)') FROM "+ sDatabasename+"."+sUser+".[GDB_ITEMS] WHERE Name='"+sDatabasename+"."+sUser+"."+sTableName+"'"; SqlCommand cmd = GetCommand(sql); SqlDataReader reader = cmd.ExecuteReader(); while (reader.Read()) { SRID= reader.GetSqlValue(0); } return SRID; } }}
以上代码有几个需要说明

1:在使用Geometry对象解析过程中,使用Deserialize,该方法只有SQL Server2012有,如果你使用SQL Server2008没有该方法

2:Geometry和Geography的区别在于你所使用的投影是平面坐标和地理坐标

3:在使用空间关系中,系统会提示

Unable to load DLL 'SqlServerSpatial110.dll': 找不到指定的模块。 (Exception from HRESULT: 0x8007007E)
这是因为,Microsoft.SqlServer.Types.dll文件需要使用操作系统C:\Windows\System32\SqlServerSpatial110.dll(同样安装了SQL Server不同版本,在该路径下的版本号不一样,110代表2012版本),该dll不是加载的,是需要存储放在系统路径下的,注意两者的版本一致。

4:获得SRID,我是直接从ArcSDE的Schema的XML来获得的。

最后强调一下,因为这是Mircosoft提供的空间存储对象,所以相关帮助查看微软帮助即可。

http://technet.microsoft.com/zh-cn/library/ee642046(v=sql.105).aspx

更深一步,如果对该方面的内容非常感兴趣,建议看看

SQL Server Spatial Tools
-------------------------------------------------------------------------------------------------------

版权所有,文章允许转载,但必须以链接方式注明源地址,否则追究法律责任!

------------------------------------------------------------------------------------------------------

版权声明:本文为博主原创文章,未经博主允许不得转载。

你可能感兴趣的文章
java中数据流的简单介绍
查看>>
根据物流号查看物流信息
查看>>
jsp设置MIME类型
查看>>
python模拟自动登录网站(urllib2)
查看>>
Java 对文件的操作
查看>>
洛谷 题解 P3627 【[APIO2009]抢掠计划】
查看>>
springboot传入json和文件_SpringBoot系列教程22-整合SpringMVC之HttpMessageConverters
查看>>
不礼让行人怎么抓拍的_张家川公安交警持续曝光机动车不礼让行人【第24期】...
查看>>
用pythonturtle写名字_去年爆款新生儿名字,家长自以为起的不错,却有“棺材”的意思...
查看>>
句子分类_语法微课句子的分类+文本讲解
查看>>
显示提示_体检报告显示:“转氨酶”升高!提示身体可能出现了这些健康问题...
查看>>
图形化分析工具_推荐一款基于小米 soar 的开源 sql 分析与优化的 web 图形化工具...
查看>>
485 工控机 接线方式_RS485温湿度传感器的接线方式及注意事项
查看>>
12306排队是什么意思_12306订单请求排队中是什么意思 要等多久
查看>>
u3d游戏开发视频潭州_unity3d教程视频-unity3d教程中文零基础入门/u3d游戏开发/特效案例/项目实战V2.0 最新版 - 极光站...
查看>>
c++区块链实例_cpp 区块链模拟示例(二)工程代码解析
查看>>
hourglass论文_论文笔记 Stacked Hourglass Networks for Human Pose Estimation
查看>>
java 接口的本质_Java基本概念:接口
查看>>
java死锁的解决_java中常见的死锁以及解决方法代码
查看>>
java菜单栏不下拉_我java代码中的下拉列表设好后为什么无法下拉?
查看>>