将新列属性添加到 shapefile 并使用 Geotools Java 将其保存到数据库
Add new column attribute to the shapefile and save it to database using Geotools Java
我正在通过添加新的列属性来转换 shapefile。由于此任务是使用 Java 执行的,所以我现在知道的唯一选择是使用 Geotools。我有 2 个主要问题:
1.我无法弄清楚如何实际添加一个新的列变量。 feature.setAttribute("col","value")是答案吗?
我从这个 post 中看到了示例:https://gis.stackexchange.com/questions/215660/modifying-feature-attributes-of-a-shapefile-in-geotools 但我没有得到解决方案。
//Upload the ShapeFile
File file = JFileDataStoreChooser.showOpenFile("shp", null);
Map<String, Object> params = new HashMap<>();
params.put("url", file.toURI().toURL());
DataStore store = DataStoreFinder.getDataStore(params);
SimpleFeatureSource featureSource = store.getFeatureSource(store.getTypeNames()[0]);
String typeName = store.getTypeNames()[0];
FeatureSource<SimpleFeatureType, SimpleFeature> source =
store.getFeatureSource(typeName);
Filter filter = Filter.INCLUDE;
FeatureCollection<SimpleFeatureType, SimpleFeature> collection = source.getFeatures(filter);
try (FeatureIterator<SimpleFeature> features = collection.features()) {
while (features.hasNext()) {
SimpleFeature feature = features.next();
//adding new columns
feature.setAttribute("ShapeID", "SHP1213");
feature.setAttribute("UserName", "John");
System.out.print(feature.getID());
System.out.print(":");
System.out.println(feature.getDefaultGeometryProperty().getValue());
}
}
/*
* Write the features to the shapefile
*/
Transaction transaction = new DefaultTransaction("create");
// featureSource.addFeatureListener(fl);
if (featureSource instanceof SimpleFeatureStore) {
SimpleFeatureStore featureStore = (SimpleFeatureStore) featureSource;
featureStore.setTransaction(transaction);
try {
featureStore.addFeatures(collection);
transaction.commit();
} catch (Exception problem) {
problem.printStackTrace();
transaction.rollback();
} finally {
transaction.close();
}
System.exit(0); // success!
} else {
System.out.println(typeName + " does not support read/write access");
System.exit(1);
}
假设 setattribute 是添加的那个,我得到上面代码的以下错误。
Exception in thread "main" org.geotools.feature.IllegalAttributeException:Unknown attribute ShapeID:null value:null
at org.geotools.feature.simple.SimpleFeatureImpl.setAttribute(SimpleFeatureImpl.java:238)
at org.geotools.Testing.WritetoDatabase.main(WritetoDatabase.java:73)
2。修改这些更改后,我想将其存储在数据库(PostGIS)中。我发现下面的代码片段完成了任务,但似乎只插入形状文件对我不起作用
Properties params = new Properties();
params.put("user", "postgres");
params.put("passwd", "postgres");
params.put("port", "5432");
params.put("host", "127.0.0.1");
params.put("database", "test");
params.put("dbtype", "postgis");
dataStore = DataStoreFinder.getDataStore(params);
上述情况中的错误是 NullPointerException。
在 GeoTools 中,(Simple)FeatureType 是不可变的(不可更改的),因此您不能只向 shapefile 添加新属性。因此,首先您必须创建一个包含新属性的新 FeatureType。
FileDataStore ds = FileDataStoreFinder.getDataStore(new File("/home/ian/Data/states/states.shp"));
SimpleFeatureType schema = ds.getSchema();
// create new schema
SimpleFeatureTypeBuilder builder = new SimpleFeatureTypeBuilder();
builder.setName(schema.getName());
builder.setSuperType((SimpleFeatureType) schema.getSuper());
builder.addAll(schema.getAttributeDescriptors());
// add new attribute(s)
builder.add("shapeID", String.class);
// build new schema
SimpleFeatureType nSchema = builder.buildFeatureType();
然后您需要将所有现有功能转换为新架构并添加新属性。
// loop through features adding new attribute
List<SimpleFeature> features = new ArrayList<>();
try (SimpleFeatureIterator itr = ds.getFeatureSource().getFeatures().features()) {
while (itr.hasNext()) {
SimpleFeature f = itr.next();
SimpleFeature f2 = DataUtilities.reType(nSchema, f);
f2.setAttribute("shapeID", "newAttrValue");
//System.out.println(f2);
features.add(f2);
}
}
最后,打开 Postgis 数据存储并将新功能写入其中。
Properties params = new Properties();
params.put("user", "postgres");
params.put("passwd", "postgres");
params.put("port", "5432");
params.put("host", "127.0.0.1");
params.put("database", "test");
params.put("dbtype", "postgis");
DataStore dataStore = DataStoreFinder.getDataStore(params);
SimpleFeatureSource source = dataStore.getFeatureSource("tablename");
if (source instanceof SimpleFeatureStore) {
SimpleFeatureStore store = (SimpleFeatureStore) source;
store.addFeatures(DataUtilities.collection(features));
} else {
System.err.println("Unable to write to database");
}
我正在通过添加新的列属性来转换 shapefile。由于此任务是使用 Java 执行的,所以我现在知道的唯一选择是使用 Geotools。我有 2 个主要问题:
1.我无法弄清楚如何实际添加一个新的列变量。 feature.setAttribute("col","value")是答案吗?
我从这个 post 中看到了示例:https://gis.stackexchange.com/questions/215660/modifying-feature-attributes-of-a-shapefile-in-geotools 但我没有得到解决方案。
//Upload the ShapeFile
File file = JFileDataStoreChooser.showOpenFile("shp", null);
Map<String, Object> params = new HashMap<>();
params.put("url", file.toURI().toURL());
DataStore store = DataStoreFinder.getDataStore(params);
SimpleFeatureSource featureSource = store.getFeatureSource(store.getTypeNames()[0]);
String typeName = store.getTypeNames()[0];
FeatureSource<SimpleFeatureType, SimpleFeature> source =
store.getFeatureSource(typeName);
Filter filter = Filter.INCLUDE;
FeatureCollection<SimpleFeatureType, SimpleFeature> collection = source.getFeatures(filter);
try (FeatureIterator<SimpleFeature> features = collection.features()) {
while (features.hasNext()) {
SimpleFeature feature = features.next();
//adding new columns
feature.setAttribute("ShapeID", "SHP1213");
feature.setAttribute("UserName", "John");
System.out.print(feature.getID());
System.out.print(":");
System.out.println(feature.getDefaultGeometryProperty().getValue());
}
}
/*
* Write the features to the shapefile
*/
Transaction transaction = new DefaultTransaction("create");
// featureSource.addFeatureListener(fl);
if (featureSource instanceof SimpleFeatureStore) {
SimpleFeatureStore featureStore = (SimpleFeatureStore) featureSource;
featureStore.setTransaction(transaction);
try {
featureStore.addFeatures(collection);
transaction.commit();
} catch (Exception problem) {
problem.printStackTrace();
transaction.rollback();
} finally {
transaction.close();
}
System.exit(0); // success!
} else {
System.out.println(typeName + " does not support read/write access");
System.exit(1);
}
假设 setattribute 是添加的那个,我得到上面代码的以下错误。
Exception in thread "main" org.geotools.feature.IllegalAttributeException:Unknown attribute ShapeID:null value:null
at org.geotools.feature.simple.SimpleFeatureImpl.setAttribute(SimpleFeatureImpl.java:238)
at org.geotools.Testing.WritetoDatabase.main(WritetoDatabase.java:73)
2。修改这些更改后,我想将其存储在数据库(PostGIS)中。我发现下面的代码片段完成了任务,但似乎只插入形状文件对我不起作用
Properties params = new Properties();
params.put("user", "postgres");
params.put("passwd", "postgres");
params.put("port", "5432");
params.put("host", "127.0.0.1");
params.put("database", "test");
params.put("dbtype", "postgis");
dataStore = DataStoreFinder.getDataStore(params);
上述情况中的错误是 NullPointerException。
在 GeoTools 中,(Simple)FeatureType 是不可变的(不可更改的),因此您不能只向 shapefile 添加新属性。因此,首先您必须创建一个包含新属性的新 FeatureType。
FileDataStore ds = FileDataStoreFinder.getDataStore(new File("/home/ian/Data/states/states.shp"));
SimpleFeatureType schema = ds.getSchema();
// create new schema
SimpleFeatureTypeBuilder builder = new SimpleFeatureTypeBuilder();
builder.setName(schema.getName());
builder.setSuperType((SimpleFeatureType) schema.getSuper());
builder.addAll(schema.getAttributeDescriptors());
// add new attribute(s)
builder.add("shapeID", String.class);
// build new schema
SimpleFeatureType nSchema = builder.buildFeatureType();
然后您需要将所有现有功能转换为新架构并添加新属性。
// loop through features adding new attribute
List<SimpleFeature> features = new ArrayList<>();
try (SimpleFeatureIterator itr = ds.getFeatureSource().getFeatures().features()) {
while (itr.hasNext()) {
SimpleFeature f = itr.next();
SimpleFeature f2 = DataUtilities.reType(nSchema, f);
f2.setAttribute("shapeID", "newAttrValue");
//System.out.println(f2);
features.add(f2);
}
}
最后,打开 Postgis 数据存储并将新功能写入其中。
Properties params = new Properties();
params.put("user", "postgres");
params.put("passwd", "postgres");
params.put("port", "5432");
params.put("host", "127.0.0.1");
params.put("database", "test");
params.put("dbtype", "postgis");
DataStore dataStore = DataStoreFinder.getDataStore(params);
SimpleFeatureSource source = dataStore.getFeatureSource("tablename");
if (source instanceof SimpleFeatureStore) {
SimpleFeatureStore store = (SimpleFeatureStore) source;
store.addFeatures(DataUtilities.collection(features));
} else {
System.err.println("Unable to write to database");
}