8

I'm new to all this GIS business, and am developing a Java web app using the JTS library. I'm trying to get my head around the JTS classes and how they're supposed to be used.

I have some existing code in which every spatial property is stored as a Geometry object, whether it's a Point or a Polygon. I understand that abstraction is generally nice, but if something is definitely a point (like Building.centerPoint), then surely it should be a Point type property? I'm further confused by the fact that the WKTReader returns a Geometry object no matter what type of WKT string you feed it (POINT or POLYGON), and that there does not appear to be any obvious way to convert such a Geometry object to a Point object without an ugly downcast or presumptive geomFactory.createPoint(geom.getCoordinate()), which is basically an implicit downcast anyway (it's probably not what you want if geom is a Polygon).

So my question is: is it good practice to manage all spatial objects as abstract Geometry instances? As motivational corollaries:

  • If not, what is the canonical way to convert a String to a Point?
  • If so, how should one determine the specific type of Geometry? For instance, if I want to validate that the user provided a Point rather than a Polygon?

I realise that functionally the distinction may not be of great importance; a Point may just have an area of zero, for instance, or perhaps a Polygon with a single coordinate should just be treated the same as a Point. However I'm primarily concerned with data storage and conversion, since I'm working with Spring Roo and I don't want any information getting lost or confused along the way.

2 Answers 2

2

I have been using NetTopologySuite(a C# port of JTS) for a while. So I assume that most things stay the same as that of JTS. Hopefully Java code could be similar to the c# ones :)

My attempts answering some questions..

what is the canonical way to convert a String to a Point?

A direct casting from IGeometry to IPoint has worked as the below code worked in c#

static void Main(string[] args)
        {
            WKTReader wktReader = new WKTReader();
            IGeometry ptGeometry = wktReader.Read("POINT(0 0)");

            IPoint point = (IPoint)ptGeometry;
            //printing the coordinates X,Y
            Console.WriteLine(point.X.ToString() + "," + point.Y.ToString());

            IGeometry lineGeometry = wktReader.Read("LINESTRING (30 10, 10 30, 40 40)");
            ILineString lineString = (ILineString)lineGeometry;
            //Printing Start and End Points of LineString
            Console.WriteLine(lineString.StartPoint.ToString() + "," + lineString.EndPoint.ToString());

            IGeometry polygonGeometry = wktReader.Read("POLYGON ((30 10, 10 20, 20 40, 40 40, 30 10))");
            IPolygon polygon = (IPolygon)polygonGeometry;
            Console.WriteLine(polygon.Centroid.ToString());
            Console.ReadLine();

        }

If so, how should one determine the specific type of Geometry? For instance, if I want to validate that the user provided a Point rather than a Polygon?

You could do something like below.

   IGeometry ptGeometry = wktReader.Read("POINT(0 0)");
    if (ptGeometry is IPoint)
    {
        //its a point
    }

is it good practice to manage all spatial objects as abstract Geometry instances?

I am not sure whether it is a good practice. But this is the way that it has worked for me. For example, If we are doing any spatial operations like intersect/contain, the parameters and the output of such functions are always IGeometry. So it is a good reason to work with the abstract Geometries.

For Example, the method to get the intersection of two geometries(whether they are line,point or polygon) is as shown below.

IGeometry Intersection(IGeometry other);
3
  • Thanks vinayan, that's a very helpful answer from which I'm a little more confident that I'm not completely crazy. It makes some slightly unintuitive sense that Geometry could be used for everything. I realise that I drifted away from asking a precise question, so I'll see if any other 'opinions' come through before accepting. Cheers!
    – Pie21
    Commented Aug 29, 2012 at 14:35
  • @underdark - isn't it better to add JTS somewhere in the title?Seems to be a JTS Specific question.
    – vinayan
    Commented Aug 29, 2012 at 14:56
  • I agree, but it's still better than my old title. I always get a bit carried away :). I snuck a sneaky JTS back in anyway.
    – Pie21
    Commented Aug 30, 2012 at 14:10
1

I think it depends.

ESRI's geometric library is similar to JTS, but you need to think about readability and maintenance.

Why do you need to check your geometries type everytime you pass them around? That is unnecessary and riddles your code with if clauses that do nothing. Java is statically typed, so, go ahead and use your types.

If you have a method that takes two points to work, do not ask for two IGeometry. Ask for two IPoints. It will make your code easier to read and use.

Whenever you need an IGeometry you can easily cast the more specialized types. As far as the result of other methods, such as the intersects method, they return IGeometry because the method itself will accept any kind of geometries and you do not know beforehand they return types, hence, the IGeometry return.

1
  • I would prefer to use Point for Points, but the JTS library does not appear to encourage this, since there's no apparent way to parse a WKT string directly into a Point; presumably it's parsed into a Point behind the scenes, but it's returned as a Geometry object. I realise I could cast it to a Point myself, but am wondering if I should, especially since basically every JTS function asks for Geometry parameters. I suspect I will in the end.
    – Pie21
    Commented Aug 31, 2012 at 7:37

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.