At 02:22 PM 3/27/2011 +1100, Michael Bedward wrote:
Thanks
The problem I have been having is apparently related to how I set the
schema. I am using one from the existing file, and modifying it (the first
element) from MultiPolygon to LineString. When I dump everything out, it
looks fine, but when I try to write it to a shapefile... boom, an exception
is thrown.
It is driving me nuts. Unfortunately, it appears I need to understand all
the details of what a type really means to build one. Sigh.
I am taking the suggestion to post my code. It is quite a bit, as I don't
know which things I am doing are necessary and which are redundant.
However, you may be able to quickly see whatever I'm doing that's wrong. I
am not even trying, at this point, to maintain the attributes of each line
segment, because they are not important for the final solution.
Anyway, the whole mess is at http://snippets.dzone.com/posts/show/13059
If you have the JTS libraries and geotools 2.7-M2, that single source file
will compile and run. (I am using the recommended Maven approach).
However, if you un-comment the line that writes the shapefile, it will blow
up. I don't know why, and I would love to know. It may be that the code
below will create a type that works. I haven't had a chance to try it yet.
I hope that posting the code will show where I am going astray, so I don't
have to keep asking dumb questions.
============ also ========
BTW, I tried cvs2shp example, but it fails on the following (once again, a
problem with the feature type). I assume the example is out of sync with
the version of the libraries I am using.
*/
final SimpleFeatureType TYPE = DataUtilities.createType(
"Location", // <- the name for our
feature type
"location:Point:srid=4326," + // <- the geometry
attribute: Point type
"name:String" // <- a String attribute
);
"location:Point:srid=4326" is the problem - it tries to look up 4326 and
fails. I don't know what should go in there.
The exception is:
Exception in thread "main" org.geotools.feature.SchemaException: Error
decoding srs: 4326
at org.geotools.data.DataUtilities.createAttribute(DataUtilities.java:2175)
at org.geotools.data.DataUtilities.createType(DataUtilities.java:1752)
at org.geotools.data.DataUtilities.createType(DataUtilities.java:1702)
at map.examples.WriteShapeFileExample.main(WriteShapeFileExample.java:52)
Thanks
John
Hi John
> The question is due to my weak understanding of the API: Given a collection
> of LineString geometries (say, Array or LinkedList) of line strings,
how can
> I turn that back into a shapefile?
it's quite straightforward but first you need to decide what
attributes you want to associate with each LineString. Your input data
are state and county polygons, so perhaps you would want to record the
identifying code / abbreviation / whatever of each state and county
that each line string was associated with ? And for LineString that
was originally part of a country polygon boundary but not a state
boundary, would you want to have some sort of N/A code for the state
attribute, or record the state that it falls in ?
Once you know all that (and after overcoming the simplification
challenges :) can create a feature type and line shapefile something
like this (edit for whatever attributes you are working with):
private void makeShapefile(List<LineString> lines,
CoordinateReferenceSystem crs) {
SimpleFeatureTypeBuilder typeBuilder = new
SimpleFeatureTypeBuilder();
typeBuilder.setName("Political");
typeBuilder.setCRS(crs); // if you are using one
typeBuilder.add("the_geom", LineString.class);
typeBuilder.add("id", Integer.class);
typeBuilder.add("state1", String.class);
typeBuilder.add("state2", String.class);
typeBuilder.add("county1", String.class);
typeBuilder.add("county2", String.class);
final SimpleFeatureType TYPE = typeBuilder.buildFeatureType();
SimpleFeatureBuilder featureBuilder = new SimpleFeatureBuilder(TYPE);
SimpleFeatureCollection fc = FeatureCollections.newCollection();
for (LineString line : lines) {
int numVertices = line.getNumPoints();
LineSegment seg = new LineSegment(
line.getCoordinateN(0),
line.getCoordinateN(numVertices - 1));
LineData data = lineLookup.get(seg);
featureBuilder.addAll(new Object[] {
line,
data.id,
data.state1,
data.state2,
data.county1,
data.county2
});
fc.add(featureBuilder.buildFeature(String.valueOf(data.id)));
}
}
Obviously I just made up those attributes to convey the general idea.
The code assumes that you have a small class to store the attribute
data for each line; something like this...
class LineData {
int id;
String state1;
String state2;
String county1;
String county2;
}
And also a Map like this to associate the data object with each LineString.
Map<LineSegment, LineData> lineLookup;
It is using the LineString end-points, expressed as a LineSegment
object, as the key. I suggest you use a Map rather than the
Geometry.setUserData method to store the data in your LineStrings
directly. The reason is that if you put your lines through one of the
JTS XXXSimplifiers at any stage they strip the user data from the
Geometries.
Once you've got a SimpleFeatureCollection you can create a new
shapefile from it as in the cvs2shp example:
http://docs.geotools.org/stable/userguide/examples/csv2shp.html
Michael
------------------------------------------------------------------------------
Enable your software for Intel(R) Active Management Technology to meet the
growing manageability and security demands of your customers. Businesses
are taking advantage of Intel(R) vPro (TM) technology - will your software
be a part of the solution? Download the Intel(R) Manageability Checker
today! http://p.sf.net/sfu/intel-dev2devmar
_______________________________________________
Geotools-gt2-users mailing list
Geotools-gt2-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/geotools-gt2-users