OCCI上载空间数据

众所周知,数据是GIS的血液,一个GIS系统最重要的是数据,而且在整个系统的建设过程中的花费也比较大。为此,许多GIS厂商和数据库厂商逐渐推出空间数据的存储解决方案。

其中Oracle Spatial是目前最大的数据库厂商Oracle公司推出的新一代空间数据库,它采用对象关系型数据存储模式来存储空间数据。

空间数据在Oracle中是以SDO_GEOMETRY数据类型来存储的,它的定义为:

 

SQL> desc sdo_geometry

 名称                                     是否为空?类型

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

 

 SDO_GTYPE                                          NUMBER

 SDO_SRID                                           NUMBER

 SDO_POINT                                          MDSYS.SDO_POINT_TYPE

 SDO_ELEM_INFO                                      MDSYS.SDO_ELEM_INFO_ARRAY

 SDO_ORDINATES                                      MDSYS.SDO_ORDINATE_ARRAY

 

具体的字段解释在这里就不详细说明,可以参见oracle的官方文档或者有关书籍。

首先,用oracle类型转换工具(OTT)把SDO_GEOMETRY数据类型转换成高级语言源程序文件。

D:\>ott userid=scott/tiger intype=demoin.tpy outtype=demoout.tpy code=cpp hfile=

sdogeometry.h cppfile=sdogeometry.cpp mapfile=mappings.cpp attraccess=private

转换后生成了四个C++源文件和头文件。

 

下面的代码是插入一个矩形。

#include <iostream>
#include <occi.h>
#include <assert.h>

#include "mappings.h"
#include "sdogeometry.h"

using namespace oracle::occi;
using namespace std;

const int SDO_GTYPE = 2003;

int main () 
{
	Environment *env = NULL;
	Connection *conn = NULL;
	Statement *stmt = NULL;
	ResultSet *rs = NULL;

	string username = "scott";						//用户名
	string password = "tiger";						//密码
	string connstring = "//localhost:1521/ORCL";	//连接字符串
	string sql,strname;
	int errNum = 0;
	string errMsg = "";

	env = Environment::createEnvironment(Environment::OBJECT); //创建一个环境变量
	mappings(env);		//注册函数
	try 
	{
		assert(env != NULL);
		conn = env->createConnection(username,password,connstring); //创建一个数据库连接对象
		stmt = conn->createStatement(); //创建一个Statement对象
	} 

	catch (SQLException ex) 
	{
		errNum = ex.getErrorCode();
		errMsg = ex.getMessage();
		cout << "Error Number : "<< errNum << endl; //取出异常代码
		cout << "Error Message :" <<errMsg << endl; //取出异常信息
	}

	//数据处理部分
	sql = "Insert Into spatial(geoloc) VALUES (:1)";

	try
	{
		Number srid_null;					   //SRID
		srid_null.setNull();
		sdo_point_type *point_type = new sdo_point_type();	 //SDO_POINT_TYPE
		point_type->setNull();

		vector<Number> sdo_elem_info,sdo_ordinates;	//元素信息和坐标数据
		sdo_elem_info.clear();
		sdo_ordinates.clear();
		sdo_elem_info.push_back(1);
		sdo_elem_info.push_back(1003);
		sdo_elem_info.push_back(3);

		sdo_ordinates.push_back(1);
		sdo_ordinates.push_back(1);
		sdo_ordinates.push_back(5);
		sdo_ordinates.push_back(7);

		SDO_GEOMETRY *sdo_geometry = new SDO_GEOMETRY();
		sdo_geometry->setsdo_gtype(SDO_GTYPE);
		sdo_geometry->setsdo_srid(srid_null);
		sdo_geometry->setsdo_point(point_type);
		sdo_geometry->setsdo_elem_info(sdo_elem_info);
		sdo_geometry->setsdo_ordinates(sdo_ordinates);
		stmt->setSQL(sql);
		stmt->setObject(1,sdo_geometry); //设置对象
		stmt->executeUpdate();			 //执行更新操作

		delete sdo_geometry;
	}

	catch (SQLException ex) 
	{
		errNum = ex.getErrorCode();
		errMsg = ex.getMessage();
		cout << "Error Number : "<< errNum << endl; //取出异常代码
		cout << "Error Message :" <<errMsg << endl; //取出异常信息
	}

	conn->terminateStatement(stmt); //终止Statement对象
	env->terminateConnection(conn); //断开数据库连接
	Environment::terminateEnvironment(env); //终止环境变量

	return 1;
}


 

插入后,查询的结果如下:

SQL> select * from spatial;

 

GEOLOC(SDO_GTYPE, SDO_SRID, SDO_POINT(X, Y, Z), SDO_ELEM_INFO, SDO_ORDINATES)

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

SDO_GEOMETRY(2003, NULL, NULL, SDO_ELEM_INFO_ARRAY(1, 1003, 3), SDO_ORDINATE_ARRAY(1, 1, 5, 7))

 

这只是对示例数据进行上载,还需要对实际的地理空间数据进行测试,比如shapefile文件的上载。

 

读取和一般的关系型数据读取一样,只不过看成是一个对象就可以了。

//以下代码是读取数据代码 
		string sqlQuery = "SELECT * FROM spatial";
		stmt->setSQL(sqlQuery);
		rs = stmt->executeQuery(sqlQuery);
		while (rs->next())
		{
			SDO_GEOMETRY* geometry = (SDO_GEOMETRY*)rs->getObject(1);
			cout<<"SDO_GTYPE: "<<unsigned int(geometry->getsdo_gtype())<<endl;
			//cout<<"SRID: "<<unsigned int(geometry->getsdo_srid())<<endl;
			
		}


 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值