ForceCoordinateSystemIterator类next()方法重类型及原对象更新疑问
ForceCoordinateSystemIterator 常见疑问解答
Q1:ForceCoordinateSystemIterator的next()方法为何要返回重类型(retype)后的SimpleFeature,而非原始对象?
ForceCoordinateSystemIterator的核心作用是强制统一要素的坐标系,源码里的builder是携带了目标坐标系的FeatureTypeBuilder实例。调用SimpleFeatureBuilder.retype(next, builder)主要做了两件关键事:
- 基于目标坐标系的FeatureType创建新的SimpleFeature对象,确保要素的属性结构(Schema)与目标坐标系完全匹配;
- 将原始要素的所有属性值(包括几何)复制到新对象中,同时保证几何属性的坐标系符合目标要求(比如自动转换坐标系、修正坐标系元数据)。
不是原始对象存在问题,而是原始要素的坐标系可能和预期不符,重类型处理是为了让所有流经该迭代器的要素都统一到指定坐标系下,避免后续处理因坐标系不一致出现错误。
Q2:使用ForceCoordinateSystemIterator时无法获取原始对象更新默认几何,最优解决方案是什么?
因为next()返回的是重类型后的新对象,修改它不会影响原始集合里的要素。最优方案分两种场景处理:
场景1:无需依赖ForceCoordinateSystemIterator自动转坐标系
直接读取原始要素,手动处理坐标系转换并修改几何,最后存入可修改的集合:
FeatureJSON featureJSON = new FeatureJSON(new GeometryJSON(15)); InputStream is = Files.newInputStream(Paths.get("/arjen_data/rust/2.geojson")); SimpleFeatureCollection originalCollection = (SimpleFeatureCollection) featureJSON.readFeatureCollection(is); // 创建可修改的新集合 DefaultFeatureCollection modifiedCollection = new DefaultFeatureCollection(null, originalCollection.getSchema()); try (SimpleFeatureIterator fit = originalCollection.features()) { while (fit.hasNext()) { SimpleFeature originalFeature = fit.next(); Geometry originalGeom = (Geometry) originalFeature.getDefaultGeometry(); // 若需要手动转换坐标系,可添加以下代码 // Geometry transformedGeom = JTS.transform(originalGeom, targetCRS, new GeometryFactory()); // 修改几何 Geometry intersection = originalGeom.difference(union); // 基于原始要素创建可修改副本并更新几何 SimpleFeature modifiedFeature = SimpleFeatureBuilder.copy(originalFeature); modifiedFeature.setDefaultGeometry(intersection); modifiedCollection.add(modifiedFeature); } } // 后续操作使用modifiedCollection
场景2:必须使用ForceCoordinateSystemIterator处理坐标系
如果需要该迭代器的坐标系统一能力,修改重类型后的要素后,将其存入新的可修改集合即可,无需操作原始对象:
FeatureJSON featureJSON = new FeatureJSON(new GeometryJSON(15)); InputStream is = Files.newInputStream(Paths.get("/arjen_data/rust/2.geojson")); SimpleFeatureCollection originalCollection = (SimpleFeatureCollection) featureJSON.readFeatureCollection(is); DefaultFeatureCollection modifiedCollection = new DefaultFeatureCollection(null, originalCollection.getSchema()); try (SimpleFeatureIterator fit = originalCollection.features()) { while (fit.hasNext()) { SimpleFeature retypedFeature = fit.next(); Geometry geom = (Geometry) retypedFeature.getDefaultGeometry(); Geometry intersection = geom.difference(union); // 更新重类型后的要素几何 retypedFeature.setDefaultGeometry(intersection); // 添加到新集合 modifiedCollection.add(retypedFeature); } } // 后续使用modifiedCollection
核心逻辑:GeoTools中从文件读取的原始集合通常是只读的,无论是否使用重类型对象,都应该将修改后的要素存入新的可修改集合,这是处理要素修改的标准方式。
内容的提问来源于stack exchange,提问作者Arjen10
相关产品推荐
相关产品推荐

