OGR根据FID删除矢量中的某个要素(多边形)

来源:互联网 发布:java工程师证书考试 编辑:程序博客网 时间:2024/04/27 15:24

这是一个函数,实现复制原来的矢量文件,然后删除掉FID与对应数组pFID中相等的要素,参数1为原来的矢量文件DataSource指针,参数2为输出的矢量文件名,参数3为存储要删除的FID的数组,参数4为结果矢量的格式。

bool CreateResultSHP(OGRDataSource *poSrcDs,std::string outputFileName,vector<int> *pFID,const char* pszFormat)
{
 //创建输出矢量文件
 OGRSFDriver *poDriver;
 if (pszFormat == NULL)
 {
  pszFormat = "ESRI Shapefile";
 }

 poDriver = OGRSFDriverRegistrar::GetRegistrar()->GetDriverByName( pszFormat );
 if (poDriver == NULL) 
 { 
  cerr<<"Creater poDriver error!"<<endl;
  return false;
 }

 //先复制一份原来的矢量文件,实验验证过使用CopyDataSource的方法可以将投影也复制
 OGRDataSource* poDstDS = poDriver->CopyDataSource(poSrcDs,outputFileName.c_str(),NULL);
 if (poDstDS == NULL)
 {
  cerr<<"Creater poDstDS error!"<<endl;
  return false;
 }
 //获取该数据源的图层数量
 int nLayerCount = poDstDS->GetLayerCount(); 
 cout<<"nLayerCount = "<<nLayerCount<<endl;

 //读取该数据源中的第一个图层
 OGRLayer *_Layer = poDstDS->GetLayer(0);
 if (_Layer == NULL)
 {
  cout<<"Layer Error!"<<endl;
  return 0;
 }
 //读取该图层的定义
 OGRFeatureDefn *pFeatureDefn = NULL;
 pFeatureDefn = _Layer->GetLayerDefn();

 //读取该图层的名称
 std::string strLayerName = pFeatureDefn->GetName();

 //读取图层的字段个数
 int nFieldCount = 0;
 nFieldCount = pFeatureDefn->GetFieldCount();

 //获取每个Feature
 OGRFeature *_Feature;
 OGRFieldDefn *pFieldDefn = NULL;
 OGRFieldType fieldtype;
 _Layer->ResetReading();//从头开始读取

/* -------------------------------------------------------------------- */
/*      循环处理每一个Feature,Feature包括形状Geometry和属性Field       */
/* -------------------------------------------------------------------- */

 while ((_Feature = _Layer->GetNextFeature()) != NULL)
 {
  //根据字段名称获取字段的内容
  long iFID = _Feature->GetFID();
  for (int i = 0;i<pFID->size();i++)
  {

    if(abs(pFID->at(i) - iFID) < 0.00001)
   {
         _Layer->DeleteFeature(iFID);
    }

  }
 }
 std::string strSQL = "REPACK " + strLayerName;
 poDstDS->ExecuteSQL(strSQL.c_str(),NULL,"");    //此句非常关键,如果只用DeleteFeature只是把dbf文件里FID为该值的要素标记为deleted,但实际上并未将该feature真正删除,利用REPACK命令,将忽略标记为deleted的feature。
 OGRDataSource::DestroyDataSource(poDstDS);
 cout<<"Create result shp file completed!"<<endl;
 return true;

}