Category Archives: general

Creating sample points in a polygon with OGR and Shapely (Introduction)

Creating sample points for a given region of interest is a common task in geospatial analysis. It is therefore logically consistent that there is already a number of ways available to create some including the Create Random Points tool of the ArcToolbox in ArcGIS or the corresponding components of the fTools plugin for QGIS. As I’m trying to follow an explicit under-the-hood-philosophy, I will – starting with this very first “real” entry at Portolan – implement my very own sampling methodology for anyone willing to follow.

As it is my (current) programming language of choice I will use Python to accomplish my task. Adding to the fact that I have plenty of working experience with it, Python has the advantage of being very well positioned in the realm of geospatial processing. This is courtesy of a wide range of libraries dealing with corresponding tasks including two that I will use extensively, namely OGR (as part of GDAL) and Shapely. While OGR serves as a well suited toolbox for all things vector – including export and import to external file and/or database formats, basic dataset creation and editing as well as more sophisticated procedures such as generalization – I have found Shapely (basically representing a Pythonic interface to libgeos that is also used by OGR itself) to be a more direct link to the topological operations that are bread and butter for any kind of geographical information system.

As Python explicitly encourages the object-oriented programming paradigm, I will follow that and implement my very own PolygonPointSampler in compliance to that paradigm. Mind you, I’m not an explicitly stated computer scientist, but a cartographer by trait that somehow turned into a mostly self-taught specialist for geoinformatics. My theoretical ramblings with regard to programming may be a little off from time to time, however all of the things presented here do actually work in practice – which is most important for me. And maybe for the reader as well.

Corresponding to these prerequisites a base class for a PolygonPointSampler could be implemented as set out in the following listing:

u"""
A base class for creating sample points located in a given region of interest,
i.e. polygon.
"""

from shapely.geometry import Polygon

class PolygonPointSampler(object):

    def __init__(self, polygon = ''):
        u"""
        Initialize a new PolygonPointSampler object using the specified polygon
        object (as allocated by Shapely). If no polygon is given a new empty
        one is created and set as the base polygon.
        """
        if polygon:
            self.polygon = polygon
        else:
            self.polygon = Polygon()
        self.samples = list()
        self.sample_count = 0
        self.prepared = False

    def add_polygon(self, polygon):
        u"""
        Add another polygon entity to the base polygon by geometrically unifying
        it with the current one.
        """
        self.polygon = self.polygon.union(polygon)
        self.prepared = False

    def print_samples(self):
        u"""
        Print all sample points using their WKT representation.
        """
        for sample_pt in self.samples:
            print sample_pt

    def prepare_sampling(self):
        u"""
        Prepare the actual sampling procedure by splitting up the specified base
        polygon (that may consist of multiple simple polygons) and appending its
        compartments to a dedicated list.
        """
        self.src = list()
        if hasattr(self.polygon, 'geoms'):
            for py in self.polygon:
                self.src.append(py)
        else:
            self.src.append(self.polygon)
        self.prepared = True

    def perform_sampling(self):
        u"""
        Create a stub for the actual sampling procedure.
        """
        raise NotImplementedError

 

Welcome to Portolan…

“A catalog of directions to be followed between notable points.” 1

This is how Portolan charts – or rhumb maps as they are called as well – have been defined by historians of cartography. While this rather barren definition gives no impression of the perils and hazards of medieval seafaring, it adequately captures the essence of the guides that have been used for this kind of endeavors. It also helps to explain what I’m starting today with this blog – albeit not with regard to maritime navigation but concerning the geospatial, database and programming domains.

Easiest to determine are the “notable points” that the Portolan Blog is going to cover following this introductory post. These points of interest include first and foremost data analysis, remote sensing, geographical information systems, database systems, cartography, and data visualization.

The comprising bracket under which all these subjects are to be illuminated – or better: the manner of the “directions” that I will be giving – is programming code, naturally in one of the languages that I’m reasonably acquainted with, namely Python, IDL or at times Java. Where this does not apply, the directions given will at least include some kind of hint, advice or pointer that is to alleviate the reader’s work in one of the noted fields of interest.

Finally, the term “catalog” refers to the systematic and list-like character of the underlying creation. In case of the Portolan Blog I’d like to kindly ask the reader to bear with me if the result at first glance does seem to lack any kind of system or is accompanied by a little too much elaborated blathering on my behalf to be called a simple list. Here I take myself the liberty to deviate from the definition as this is not supposed to be an exercise in compliance to rules but should be fun as well.

Stating this I’m about to end my first post wishing the reader and myself the necessary stamina, blazing creativity and a sufficient amount of time to accomplish this endeavor.

  1. Michel Mollat du Jourdin and Monique de La Ronciere: Sea Charts of the Early Explorers: 13th to 17th Century, London, Thames and Hudson, 1984